> ## Documentation Index
> Fetch the complete documentation index at: https://dragonwingdocs.qualcomm.com/llms.txt
> Use this file to discover all available pages before exploring further.

# 不使用 Yocto 构建内核

独立工作流允许您在不构建完整 Yocto 镜像的情况下编译、测试和部署内核更改。所有必需的交叉编译和镜像打包工具都捆绑在 `kmake-image` Docker 容器中。

## 限制和注意事项

<Warning>
  独立工作流仅构建和打包内核与模块。它不生成根文件系统。要构建或修改依赖完整 Yocto BSP 的树外（out-of-tree）内核模块，请改用基于 Yocto 的工作流。
</Warning>

* **工具链**：`kmake-image` Docker 镜像提供 `aarch64` 交叉工具链、`systemd ukify` 和镜像打包脚本。无需在主机上安装工具链。
* **DTB 打包**：独立构建时，必须使用 [qcom-dtb-metadata](https://github.com/qualcomm-linux/qcom-dtb-metadata) 仓库中的静态 ITS 配置手动打包 DTB。Yocto 构建则通过 `meta-qcom` 自动处理。
* **源代码版本**：要与发布构建中使用的确切源代码保持一致，请检查 `meta-qcom/recipes-kernel/linux/linux-qcom_6.18.bb` 中的 `SRCREV` 字段。

## 访问内核源代码

直接克隆内核仓库：

```bash theme={null}
git clone --branch qcom-6.18.y \
    https://github.com/qualcomm-linux/kernel.git kernel
```

**表：内核分支**

| 分支            | 用例                                |
| ------------- | --------------------------------- |
| `qcom-6.18.y` | LTS 生产构建；推荐用于 SoC 启用（bring-up）和集成 |
| `qcom-next`   | 上游贡献以及针对最新内核的验证                   |

## 设置 Docker 工具链

克隆并构建 `kmake-image` 容器：

```bash theme={null}
git clone https://github.com/qualcomm-linux/kmake-image.git
cd kmake-image
docker build --build-arg USER_ID=$(id -u) \
             --build-arg GROUP_ID=$(id -g) \
             --build-arg USER_NAME=$(whoami) \
             -t kmake-image .
cd ..
```

为方便起见，设置 shell 别名。将这些别名添加到您的 shell 配置文件中，以便在会话之间保留：

```bash theme={null}
alias kmake-image-run='docker run -it --rm \
  --user $(id -u):$(id -g) \
  --workdir="$PWD" \
  -v "$(dirname $PWD)":"$(dirname $PWD)" \
  kmake-image'
alias kmake='kmake-image-run make'
```

## 收集构建产物

创建 `artifacts/` 目录，用于存放组装最终镜像所需的 ramdisk、启动二进制文件和 DTB 元数据：

```bash theme={null}
mkdir artifacts
```

**获取 initramfs ramdisk**

```bash theme={null}
wget -O artifacts/ramdisk.gz \
    http://storage.kernelci.org/images/rootfs/buildroot/buildroot-baseline/20230703.0/arm64/rootfs.cpio.gz
```

**获取 systemd-boot 二进制文件**

```bash theme={null}
wget -O artifacts/systemd-boot-efi.deb \
    http://ports.ubuntu.com/pool/universe/s/systemd/systemd-boot-efi_255.4-1ubuntu8_arm64.deb
dpkg-deb -xv artifacts/systemd-boot-efi.deb artifacts/systemd
```

**获取 DTB 元数据**

独立构建时，必须使用静态 ITS 配置手动打包 DTB。克隆 `qcom-dtb-metadata` 仓库以获取所需的 `qcom-metadata.dts` 和 `qcom-next-fitimage.its` 文件：

```bash theme={null}
git clone https://github.com/qualcomm-linux/qcom-dtb-metadata.git \
    artifacts/qcom-dtb-metadata
```

## 构建内核和模块

使用标准的 Qualcomm<sup>®</sup> 配置片段配置并构建内核，然后将模块安装到暂存目录：

```bash theme={null}
cd kernel
mkdir -p ../kobj

env -u KCONFIG_CONFIG ./scripts/kconfig/merge_config.sh -m -O ../kobj \
    arch/arm64/configs/defconfig \
    arch/arm64/configs/prune.config \
    arch/arm64/configs/qcom.config

kmake O=../kobj olddefconfig
kmake O=../kobj -j$(nproc)
kmake O=../kobj -j$(nproc) dir-pkg INSTALL_MOD_STRIP=1
```

将构建好的内核模块（DLKM）打包到 ramdisk 中：

```bash theme={null}
(cd ../kobj/tar-install ; \
 find lib/modules | cpio -o -H newc -R +0:+0 | gzip -9 >> ../../artifacts/ramdisk.gz)
```

## 打包启动镜像

**生成 `efi.bin`（ESP 分区）**

`efi.bin` 镜像包含 systemd-boot、内核（打包为 UKI 类型 2 镜像）和 initramfs：

```bash theme={null}
cd ..
# Default command line matches the Yocto UKI_CMDLINE from esp-qcom-image.bb.
# Override CMDLINE if your rootfs partition label or console differs.
CMDLINE="root=PARTLABEL=rootfs rw rootwait console=ttyMSM0,115200"
kmake-image-run generate_boot_bins.sh efi \
    --ramdisk artifacts/ramdisk.gz \
    --systemd-boot artifacts/systemd/usr/lib/systemd/boot/efi/systemd-bootaa64.efi \
    --stub artifacts/systemd/usr/lib/systemd/boot/efi/linuxaa64.efi.stub \
    --linux kobj/arch/arm64/boot/Image \
    --cmdline "${CMDLINE}" \
    --output images
```

**生成 `dtb.bin`（DTB 分区）**

为所有支持设备树的目标构建基于 FIT 的 `dtb.bin`：

```bash theme={null}
kmake-image-run make_fitimage.sh \
    --metadata artifacts/qcom-dtb-metadata/qcom-metadata.dts \
    --its artifacts/qcom-dtb-metadata/qcom-next-fitimage.its \
    --kobj kobj \
    --output images
```

`efi.bin` 和 `dtb.bin` 都会被放入 `images/` 目录中，可直接刷写。

## 内核镜像构建脚本

上述构建和打包步骤封装在 Docker 中包含的 `build.sh` 脚本中，可自动构建可启动的内核镜像并将其打包为 efi.bin、dtb.bin 和 boot.img。

要使用这个替代的 `build.sh` 脚本，请运行：

```bash theme={null}
kmake-image-run build.sh --dtb qcs6490-rb3gen2.dtb \
        --out kobj \
        --systemd artifacts/systemd/usr/lib/systemd/boot/efi \
        --ramdisk artifacts/ramdisk.gz \
        --images images \
        --cmdline "${CMDLINE}"
```

<Note>
  * \--dtb 参数是必需的。它指定要打包到内核镜像中的设备树 Blob。上述命令以 `qcs6490-rb3gen2.dtb` 为例。
  * 初始化 CMDLINE 以设置您的内核 cmdline 参数，否则将使用默认的通用值。
</Note>

## 刷写和启动

将设备置于 fastboot 模式，然后刷写两个镜像：

```bash theme={null}
fastboot flash efi images/efi.bin
fastboot flash dtb_a images/dtb.bin
fastboot reboot
```

设备重启后，按照[安装并启动内核](./install-and-boot-the-kernel#verify-the-running-kernel)中的说明验证正在运行的内核版本。
