开源鸿蒙6.1集成busybox(标准系统)
·
移植busybox
1.准备busybox源码
- 1.手动下载并解压到鸿蒙项目根目录
third_party目录下: BusyBox - 2.
wget命令拉取
wget https://www.busybox.net/downloads/busybox-1.38.0.tar.bz2
tar -jxf busybox-1.38.0.tar.bz2
# harmonyRoot为鸿蒙源码根目录
mv busybox-1.38.0.tar.bz2 harmonyRoot/third_party/busybox
2.将busybox加入GN+NINJA构建流程中
- 1.在
busybox目录下创建bundle.json文件,并添加以下内容
{
"name": "@ohos/busybox",
"description": "busybox Linux command line",
"version": "1.38.0",
"license": "GNU GENERAL PUBLIC LICENSE",
"publishAs": "code-segment",
"segment": {
"destPath": "third_party/busybox"
},
"dirs": {},
"scripts": {},
"licensePath": "",
"readmePath": {
"en": ""
},
"component": {
"name": "busybox",
"subsystem": "thirdparty",
"syscap": [],
"features": [
"busybox_feature_support_usr_symlink"
],
"adapted_system_type": [
"standard",
"small"
],
"rom": "73KB",
"ram": "146KB",
"deps": {
"components": [
"selinux",
"openssl"
],
"third_party": []
},
"build": {
"sub_component": [
"//third_party/busybox:busybox"
],
"inner_kits": [
{
"name" : "//third_party/busybox:busybox"
}
],
"test": []
}
}
}
- 2.在
busybox目录下创建busybox.gni文件,并添加以下内容
BUSYBOX_SRC_DIR = [ "//third_party/busybox" ]
declare_args() {
busybox_feature_support_usr_symlink = false
busybox_config_target = "defconfig"
# 传给 make 的并行度,0 表示按 CPU 数。
busybox_build_jobs = 0
# 是否放宽告警(-w 关闭所有告警,避免 -Werror 类问题打断编译)。
busybox_relax_warnings = true
}
- 3.在
busybox目录下创建BUILD.gn文件,并添加以下内容
import("//build/config/clang/clang.gni")
import("//build/config/sysroot.gni")
import("//build/ohos.gni")
import("busybox.gni")
if (target_cpu == "loongarch64") {
_target_triple = "loongarch64-linux-ohos"
} else if (target_cpu == "arm64") {
_target_triple = "aarch64-linux-ohos"
} else if (target_cpu == "arm") {
_target_triple = "arm-linux-ohos"
} else {
_target_triple = "loongarch64-linux-ohos"
}
_busybox_build_dir = "$target_out_dir/busybox_build"
_busybox_binary = "$_busybox_build_dir/busybox"
if (defined(ohos_lite)) {
group("busybox") {
# None
}
} else {
_clang_bin = "$clang_base_path/bin/clang"
_llvm_bin_dir = "$clang_base_path/bin"
action("busybox_make") {
script = "ohos_build_busybox.py"
inputs = [ "ohos_build_busybox.py" ]
outputs = [ _busybox_binary ]
args = [
"--src-dir",
rebase_path(".", root_build_dir),
"--build-dir",
rebase_path(_busybox_build_dir, root_build_dir),
"--config-target",
busybox_config_target,
"--clang-bin",
rebase_path(_clang_bin, root_build_dir),
"--llvm-dir",
rebase_path(_llvm_bin_dir, root_build_dir),
"--target-triple",
_target_triple,
"--sysroot",
rebase_path(sysroot, root_build_dir),
"--jobs",
"$busybox_build_jobs",
]
if (busybox_relax_warnings) {
args += [ "--relax-warnings" ]
}
}
ohos_prebuilt_executable("busybox") {
# 由 action("busybox_make") 产出的二进制。
source = _busybox_binary
# 拷贝到 target_out_dir 下的名字
output = "busybox"
deps = [ ":busybox_make" ]
symlink_target_name = [
"ip",
"vi",
"candump",
"cansend",
]
if (busybox_feature_support_usr_symlink) {
symlink_target_name += [
# "../usr/bin/ip",
# "../usr/bin/vi",
]
}
module_install_dir="bin"
part_name = "busybox"
subsystem_name = "thirdparty"
install_images = [ "system" ]
install_enable = true
}
}
3.添加busybox编译脚本
busybox源码庞大,如果采用toybox那样用gn+ninja来编译,后续维护成本极大;所以采用脚本编译的方式,只需要的BUILD.gn中调用编译脚本即可,编译完成后的产物任然交由gn构建系统管理- 在
busybox目录下创建ohos_build_busybox.py文件,并添加以下内容
#!/usr/bin/env python3
import argparse
import os
import shutil
import subprocess
import sys
def run(cmd, env=None, cwd=None):
print(">>", " ".join(cmd))
subprocess.check_call(cmd, env=env, cwd=cwd)
def main():
parser = argparse.ArgumentParser()
parser.add_argument("--src-dir", required=True,
help="busybox resource code root directory")
parser.add_argument("--build-dir", required=True,
help="out-of-tree build directory")
parser.add_argument("--config-target", default="defconfig",
help="be used to create .config")
parser.add_argument("--clang-bin", required=True,
help="clang path")
parser.add_argument("--llvm-dir", required=True,
help="llvm tools directory")
parser.add_argument("--target-triple", required=True,
help="target architecture")
parser.add_argument("--sysroot", required=True,
help="musl sysroot path")
parser.add_argument("--jobs", type=int, default=0,
help="thread number of make command, 0: use all of cpu thread")
parser.add_argument("--relax-warnings", action="store_true",
help="close all warning")
args = parser.parse_args()
# use absolute path
src_dir = os.path.abspath(args.src_dir)
build_dir = os.path.abspath(args.build_dir)
clang_bin = os.path.abspath(args.clang_bin)
llvm_dir = os.path.abspath(args.llvm_dir)
sysroot = os.path.abspath(args.sysroot)
os.makedirs(build_dir, exist_ok=True)
# 1) assemble the target compiler command
target_flags = [
"--target=" + args.target_triple,
"--sysroot=" + sysroot,
"-fPIE",
"-funsigned-char",
]
cflags = list(target_flags)
if args.relax_warnings:
cflags.append("-w")
# -D_GNU_SOURCE / -D__MUSL__ 让 busybox 在 ohos musl 下更顺
# (-D__MUSL__ 避免 musl 与内核 uapi 的 sockaddr_storage 重复定义)
cflags += ["-D_GNU_SOURCE", "-D__MUSL__",
"-DBB_VER=\"" + get_bb_ver(src_dir) + "\""]
# Concatenated cross-compilation toolchain
cc_cmd = clang_bin + " " + " ".join(cflags)
cxx_cmd = clang_bin + "++ " + " ".join(cflags)
ar_cmd = os.path.join(llvm_dir, "llvm-ar")
ld_cmd = os.path.join(llvm_dir, "ld.lld")
strip_cmd = os.path.join(llvm_dir, "llvm-strip")
nm_cmd = os.path.join(llvm_dir, "llvm-nm")
ranlib_cmd = os.path.join(llvm_dir, "llvm-ranlib")
# 2) parameters of make.
make_vars = [
"ARCH=" + arch_from_triple(args.target_triple),
"CROSS_COMPILE=",
"HOSTCC=cc",
"CC=" + cc_cmd,
"CXX=" + cxx_cmd,
"AR=" + ar_cmd,
"LD=" + ld_cmd,
"STRIP=" + strip_cmd,
"NM=" + nm_cmd,
"RANLIB=" + ranlib_cmd,
"SKIP_STRIP=y",
]
dst_config = os.path.join(build_dir, ".config")
# 3) make defconfig to create .config
run(["make", "-C", src_dir, "O=" + build_dir, "-s",
args.config_target] + make_vars)
jobs = args.jobs if args.jobs > 0 else os.cpu_count()
# 4) compile
run(["make", "-C", src_dir, "O=" + build_dir, "-j" + str(jobs)] + make_vars)
# 5) checkout
busybox_bin = os.path.join(build_dir, "busybox")
if not os.path.isfile(busybox_bin):
print("ERROR: busybox binary not found at " + busybox_bin,
file=sys.stderr)
sys.exit(1)
print("OK: built " + busybox_bin)
def get_bb_ver(src_dir):
# busybox 源码里有 include/VERSION
for name in ("include/VERSION",):
p = os.path.join(src_dir, name)
if os.path.isfile(p):
with open(p) as f:
return f.read().strip()
return "0"
def arch_from_triple(triple):
# loongarch64-linux-ohos -> loongarch
return triple.split("-")[0].rstrip("0123456789")
if __name__ == "__main__":
main()
4.在厂商产品侧添加busybox
vi vender/xxx/xxx/config.json- 在该文件中的
thirdparty子系统中添加busybox组件
{
"subsystem": "thirdparty",
"components": [
...
{
"component": "busybox",
"features": []
},
...
]
}
5.验证
- 编译完成后在
out/board_name/packages/phone/system/bin/目录下会生成busybox可执行文件和BUILD.gn文件中symlink_target_name列表中列举的链接 - 烧录镜像后即可正常使用
更多推荐


所有评论(0)