From 015ff5b9a7459e95d14ea77773d5778b5261c090 Mon Sep 17 00:00:00 2001 From: dashi <181648839+col83@users.noreply.github.com> Date: Tue, 14 Jul 2026 05:03:12 +0300 Subject: [PATCH] refactor: refactor ci workflow. add local kernel compile script --- .github/workflows/build-kernel-local.sh | 246 ++++++++++++++++++++++ .github/workflows/build.yml | 204 ------------------ .github/workflows/debug.yml | 221 ++++++++++++++++++++ .github/workflows/release.yml | 265 ++++++++++++++++++++++++ .gitignore | 1 + 5 files changed, 733 insertions(+), 204 deletions(-) create mode 100755 .github/workflows/build-kernel-local.sh delete mode 100644 .github/workflows/build.yml create mode 100755 .github/workflows/debug.yml create mode 100755 .github/workflows/release.yml diff --git a/.github/workflows/build-kernel-local.sh b/.github/workflows/build-kernel-local.sh new file mode 100755 index 000000000000..487010f3fd86 --- /dev/null +++ b/.github/workflows/build-kernel-local.sh @@ -0,0 +1,246 @@ +#!/bin/bash +set -euo pipefail + +AOSP_TOOLCHAIN_BRANCH="android16" +AOSP_CLANG_VERSION="r547379" +KERNEL_DIR="kernel" +OUTPUT_DIR="out" +CLANG_DIR="clang" + +DEVICES=( + "perseus" +) + +declare -A device_matrix +device_matrix=( + [beryllium]="Xiaomi Poco F1" + [dipper]="Xiaomi Mi 8" + [equuleus]="Xiaomi Mi 8 Pro" + [perseus]="Xiaomi Mi MIX 3" + [polaris]="Xiaomi Mi MIX 2S" + [ursa]="Xiaomi Mi 8 Explorer Edition" +) + + +log_info() { + echo -e "\033[0;32m[INFO]\033[0m $1" +} + +log_warn() { + echo -e "\033[1;33m[WARN]\033[0m $1" +} + +log_error() { + echo -e "\033[0;31m[ERROR]\033[0m $1" +} + +check_dependencies() { + log_info "Checking dependencies..." + + local missing=() + + for cmd in make git wget curl tar zip ccache gcc; do + if ! command -v "$cmd" &> /dev/null; then + missing+=("$cmd") + fi + done + + # Check binutils + if ! command -v aarch64-linux-gnu-as &> /dev/null; then + missing+=("binutils-aarch64-linux-gnu") + fi + + if ! command -v arm-linux-gnueabi-as &> /dev/null; then + missing+=("binutils-arm-linux-gnueabi") + fi + + # Check development headers and libraries via dpkg + local dpkg_packages=( + "libc6-dev" + "linux-libc-dev" + "libncurses-dev" + "libncurses6" + ) + + for pkg in "${dpkg_packages[@]}"; do + if ! dpkg-query -W -f='${Status}' "$pkg" 2>/dev/null | grep -q "install ok installed"; then + missing+=("$pkg") + fi + done + + if [ ${#missing[@]} -gt 0 ]; then + log_error "Missing dependencies: ${missing[*]}" + echo + echo "Install them with:" + echo " sudo apt-get update -q && sudo apt-get install -y ${missing[*]}" + echo + exit 2 + fi + + log_info "All dependencies installed" +} + + +setup_clang() { + log_info "Setting up Clang..." + + local clang_url="https://android.googlesource.com/platform/prebuilts/clang/host/linux-x86/+archive/refs/heads/${AOSP_TOOLCHAIN_BRANCH}-release/clang-${AOSP_CLANG_VERSION}.tar.gz" + + if [ ! -f "${CLANG_DIR}/bin/clang" ]; then + log_info "Downloading Clang ${AOSP_CLANG_VERSION}..." + echo + + mkdir -p "${CLANG_DIR}" + wget -c -t 10 -O clang.tar.gz "${clang_url}" + tar -xzf clang.tar.gz -C "${CLANG_DIR}" + rm clang.tar.gz + else + log_info "Clang already installed in ${CLANG_DIR}/" + fi + + export PATH="$PWD/${CLANG_DIR}/bin:$PATH" +} + +setup_ccache() { + export CCACHE_DIR="$PWD/.ccache" + + mkdir -p "$CCACHE_DIR" + + export CCACHE_MAXSIZE=5G + export CCACHE_NOHASHDIR=true + export CCACHE_COMPILERCHECK=content + + ccache -M "$CCACHE_MAXSIZE" +} + + +build_kernel() { + local device=$1 + + log_info "Building kernel for ${device} (${device_matrix[$device]})..."; echo + + cd "${KERNEL_DIR}" + + # Clean previous build + rm -rf "${OUTPUT_DIR}" + + # export CCACHE_LOGFILE=/tmp/ccache.log + + ccache -d "${CCACHE_DIR}" -z 1>/dev/null + + # export KBUILD_BUILD_USER="" + # export KBUILD_BUILD_HOST="" + export KBUILD_BUILD_TIMESTAMP=$(date -u -d "@$(git log -1 --format=%at 2>/dev/null || echo $(date +%s))" +"%a %b %d %H:%M:%S %Z %Y" 2>/dev/null || date -u) + + time make -j$(nproc --all) \ + O="${OUTPUT_DIR}" \ + LLVM=1 \ + LLVM_IAS=1 \ + CC="ccache clang" \ + LD=ld.lld \ + ARCH=arm64 \ + CROSS_COMPILE=aarch64-linux-gnu- \ + CROSS_COMPILE_ARM32=arm-linux-gnueabi- \ + vendor/xiaomi/mi845_defconfig \ + vendor/xiaomi/${device}.config \ + all \ + 2>&1 | tee "../build.log" + + echo >> "../build.log" + echo + echo ccache dir: "$CCACHE_DIR" + echo + du -sh "$CCACHE_DIR" + echo + ccache -d "${CCACHE_DIR}" -s | tee -a "../build.log" + + if [ ! -f "${OUTPUT_DIR}/arch/arm64/boot/Image.gz-dtb" ]; then + log_error "Image.gz-dtb not found for ${device}" + ls -la "${OUTPUT_DIR}/arch/arm64/boot/" || true + cd .. + return 1 + fi + + echo + log_info "Kernel for ${device} built successfully" + cd .. +} + +create_anykernel3() { + local device=$1 + local device_name="${device_matrix[$device]}" + + log_info "Creating AnyKernel3 for ${device} (${device_name})..." + + local ak3_dir="ak3-${device}" + + if [ ! -d "${ak3_dir}" ]; then + git clone --depth=1 https://github.com/osm0sis/AnyKernel3 "${ak3_dir}" + else + cd "${ak3_dir}" + git fetch -f origin master >/dev/null + git reset --hard FETCH_HEAD >/dev/null + git clean -fdx >/dev/null 2>&1 + cd .. + fi + + cp "${KERNEL_DIR}/${OUTPUT_DIR}/arch/arm64/boot/Image.gz-dtb" "${ak3_dir}/" + + cd "${ak3_dir}" + + sed -i \ + -e "s/kernel.string=.*/kernel.string=Kernel for ${device_name}/" \ + -e "s/device.name1=.*/device.name1=${device}/" \ + -e "s/device.name2=.*/device.name2=/" \ + -e "s/device.name3=.*/device.name3=/" \ + -e "s/device.name4=.*/device.name4=/" \ + -e "s|BLOCK=/dev/block/platform/omap/omap_hsmmc.0/by-name/boot|BLOCK=auto|" \ + anykernel.sh + + zip -qr9 "Anykernel3-${device}.zip" . -x "./.git/*" "./.github/*" "./README.md" + cd .. + + log_info "AnyKernel3 for ${device} created: ${ak3_dir}/Anykernel3-${device}.zip" +} + + +main() { + echo + check_dependencies + setup_clang + setup_ccache + echo + + # Build for each device + local success_count=0 + local fail_count=0 + + for device in "${DEVICES[@]}"; do + if build_kernel "${device}"; then + create_anykernel3 "${device}" + success_count=$((success_count + 1)) + else + log_error "Build for ${device} failed" + fail_count=$((fail_count + 1)) + fi + echo + done + + log_info "Build completed" + log_info "Successful: ${success_count}" + if [ ${fail_count} -gt 0 ]; then + log_warn "Failed: ${fail_count}" + fi + + echo "" + log_info "Created files:" + for device in "${DEVICES[@]}"; do + if [ -f "ak3-${device}/Anykernel3-${device}.zip" ]; then + local size=$(du -h "ak3-${device}/Anykernel3-${device}.zip" | cut -f1) + echo " • ${device} (${device_matrix[$device]}): ${size}" + fi + done +} + +# Run +main "$@" \ No newline at end of file diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml deleted file mode 100644 index e35f5377f681..000000000000 --- a/.github/workflows/build.yml +++ /dev/null @@ -1,204 +0,0 @@ -name: 编译内核 - -on: - push: - branches: - - dev/* - - stable/* - workflow_dispatch: - -env: - AOSP_TOOLCHAIN_BRANCH: android16 - AOSP_CLANG_VERSION: r547379 - -jobs: - build: - name: 编译内核 - permissions: { contents: write } - runs-on: ubuntu-latest - strategy: - matrix: - device: - - beryllium - - dipper - - equuleus - - perseus - - polaris - - ursa - steps: - - name: 安装软件包 - if: env.PACKAGES != '' - env: - PACKAGES: - binutils-aarch64-linux-gnu - binutils-arm-linux-gnueabi - run: | - sudo apt-get update -y -q - sudo apt-get install -y -q ${{ env.PACKAGES }} - - - name: 安装make4.4.1-2 - run: | - curl -LSs http://ftp.debian.org/debian/pool/main/m/make-dfsg/make_4.4.1-2_amd64.deb -o make.deb - sudo apt-get install -y -q ./make.deb - rm ./make.deb - - - name: 同步仓库 - uses: actions/checkout@main - with: - path: kernel - - - name: 缓存Clang - id: cache-clang - uses: actions/cache/restore@main - with: - path: clang - key: clang-${{ env.AOSP_TOOLCHAIN_BRANCH }}-${{ env.AOSP_CLANG_VERSION }} - - - name: 下载Clang - id: download_clang - if: steps.cache-clang.outputs.cache-hit != 'true' - run: | - mkdir -p clang - wget -c -t 10 "https://android.googlesource.com/platform/prebuilts/clang/host/linux-x86/+archive/refs/heads/${{ env.AOSP_TOOLCHAIN_BRANCH }}-release/clang-${{ env.AOSP_CLANG_VERSION }}.tar.gz" -O clang.tgz - tar -zxvf clang.tgz -C clang/ - - - name: 保存Clang - if: always() && steps.cache-clang.outputs.cache-hit != 'true' && steps.download_clang.outcome == 'success' - uses: actions/cache/save@main - with: - path: clang - key: clang-${{ env.AOSP_TOOLCHAIN_BRANCH }}-${{ env.AOSP_CLANG_VERSION }} - - - name: 缓存ccache - uses: hendrikmuhs/ccache-action@main - with: - key: kernel-${{ matrix.device }} - restore-keys: kernel-${{ matrix.device }} - max-size: 5G - - - name: 编译 - working-directory: kernel - env: - MAKE_ARGS: - -j$(nproc --all) - O=out - LLVM=1 - LLVM_IAS=1 - CC="ccache clang" - LD=ld.lld - ARCH=arm64 - CROSS_COMPILE=aarch64-linux-gnu- - CROSS_COMPILE_ARM32=arm-linux-gnueabi- - CONFIG_FILES: - vendor/xiaomi/mi845_defconfig - vendor/xiaomi/${{ matrix.device }}.config - lxc.config - run: | - export PATH=$GITHUB_WORKSPACE/clang/bin:$PATH - export KBUILD_BUILD_USER=${{ github.repository_owner }} - export KBUILD_BUILD_HOST=github-runner - export KBUILD_BUILD_TIMESTAMP=`date -u -d "@$(git log -1 --format=%at)" +"%a %b %d %H:%M:%S %Z %Y"` - make ${{ env.MAKE_ARGS }} ${{ env.CONFIG_FILES }} all - - - name: 打包(AnyKernel3) - run: | - git clone https://github.com/osm0sis/AnyKernel3 --depth=1 ak3 - cp kernel/out/arch/arm64/boot/Image.gz-dtb ak3/ - cd ak3 - cat >anykernel.sh <> $GITHUB_OUTPUT - echo "time=$TIME_STR" >> $GITHUB_OUTPUT - - - name: 发布 - uses: softprops/action-gh-release@master - id: release - with: - tag_name: rel-${{ steps.time.outputs.timestamp }} - name: Kernel build ${{ steps.time.outputs.time }} - prerelease: ${{ startsWith(github.ref_name, 'dev/') }} - files: | - kernel/* - - - name: 发送Telegram通知 - continue-on-error: true - run: | - IDS=(${{ join(github.event.commits.*.id, ' ') }}) - MAX=6 - if [ "${#IDS[@]}" -gt "$MAX" ]; then - COMMIT_IDS_TEXT="$(printf "%s\n" "${IDS[@]:0:$MAX}"; echo "......")" - else - COMMIT_IDS_TEXT="$(printf "%s\n" "${IDS[@]}")" - fi - MSG="\ - CI ${{ steps.time.outputs.time }} -
\
-          项目: ${{ github.repository }}
-          分支: ${{ github.ref_name }}\
-          
- 提交ID: -
$COMMIT_IDS_TEXT
\ - " - PREVIEW_OPTIONS="{ \ - \"url\": \"${{ steps.release.outputs.url }}\", \ - \"prefer_small_media\": true, \ - \"show_above_text\": true \ - }" - BUTTONS="{\"inline_keyboard\": [ [ \ - { \"text\": \"下载链接\", \"url\": \"${{ steps.release.outputs.url }}\" }, \ - { \"text\": \"对比差异\", \"url\": \"${{ github.event.compare }}\" } \ - ] ] }" - curl -LSs -X POST https://api.telegram.org/bot${{ secrets.TELEGRAM_BOT_TOKEN }}/sendMessage \ - -d "chat_id=${{ vars.TELEGRAM_CHAT_ID }}" \ - -d "message_thread_id=${{ vars.TELEGRAM_MESSAGE_THREAD_ID }}" \ - -d "parse_mode=HTML" \ - --data-urlencode "text=$MSG" \ - -d "link_preview_options=$PREVIEW_OPTIONS" \ - -d "reply_markup=$BUTTONS" \ - -o response.txt && \ - (! ${{ startsWith(github.ref_name, 'stable/') }} || \ - curl -LSs -X POST https://api.telegram.org/bot${{ secrets.TELEGRAM_BOT_TOKEN }}/pinChatMessage \ - -d "chat_id=${{ vars.TELEGRAM_CHAT_ID }}" \ - -d "message_id=$(jq '.result.message_id' response.txt)") - if [ "${{ runner.debug }}" = "1" ]; then - cat response.txt - fi diff --git a/.github/workflows/debug.yml b/.github/workflows/debug.yml new file mode 100755 index 000000000000..45fa95a00baa --- /dev/null +++ b/.github/workflows/debug.yml @@ -0,0 +1,221 @@ +name: Build debug kernel + +on: + workflow_dispatch: + +env: + AOSP_TOOLCHAIN_BRANCH: android16 + AOSP_CLANG_VERSION: r547379 + +jobs: + build: + timeout-minutes: 60 + name: Build kernel + permissions: { contents: read } + runs-on: ubuntu-26.04 + strategy: + fail-fast: true + matrix: + include: + - device: beryllium + device_name: "Xiaomi Poco F1" + boot_block: auto + is_primary: true + #- device: dipper + # device_name: "Xiaomi Mi 8" + # boot_block: auto + # is_primary: false + #- device: equuleus + # device_name: "Xiaomi Mi 8 Pro" + # boot_block: auto + # is_primary: false + #- device: perseus + # device_name: "Xiaomi Mi MIX 3" + # boot_block: auto + # is_primary: false + #- device: polaris + # device_name: "Xiaomi Mi MIX 2S" + # boot_block: auto + # is_primary: false + #- device: ursa + # device_name: "Xiaomi Mi 8 Explorer Edition" + # boot_block: auto + # is_primary: false + steps: + - name: Install dependencies + run: | + dependencies=( + ccache + binutils-aarch64-linux-gnu + binutils-arm-linux-gnueabi + make + ) + + sudo apt-get update -y -q + sudo apt-get install -y -q "${dependencies[@]}" --no-install-recommends + + - name: Sync repo + uses: actions/checkout@v7 + with: + path: kernel + fetch-depth: 1 + show-progress: false + + - name: Cache Clang + id: cache-clang + uses: actions/cache/restore@v6 + with: + path: clang + key: clang-${{ env.AOSP_TOOLCHAIN_BRANCH }}-${{ env.AOSP_CLANG_VERSION }} + + - name: Setup Clang + id: download_clang + if: steps.cache-clang.outputs.cache-hit != 'true' + run: | + mkdir -p "clang/" + wget -c -t 10 -O "clang.tar.gz" "https://android.googlesource.com/platform/prebuilts/clang/host/linux-x86/+archive/refs/heads/${{ env.AOSP_TOOLCHAIN_BRANCH }}-release/clang-${{ env.AOSP_CLANG_VERSION }}.tar.gz" + tar -zxf "clang.tar.gz" -C "clang/" + + - name: Save Clang + if: steps.cache-clang.outputs.cache-hit != 'true' && steps.download_clang.outcome == 'success' + uses: actions/cache/save@v6 + with: + path: clang + key: clang-${{ env.AOSP_TOOLCHAIN_BRANCH }}-${{ env.AOSP_CLANG_VERSION }} + + - name: Setup ccache + run: | + mkdir -p .ccache + ccache -M 5G + + - name: Restore ccache + id: ccache + uses: actions/cache/restore@v6 + with: + path: .ccache + key: ccache-kernel-${{ github.run_id }} + restore-keys: | + ccache-kernel- + + - name: Reset ccache statistics + run: | + ccache -d .ccache -z + + - name: Compile kernel + working-directory: kernel + env: + CCACHE_DIR: ${{ github.workspace }}/.ccache + CCACHE_NOHASHDIR: 1 + CCACHE_COMPILERCHECK: content + CCACHE_BASEDIR: ${{ github.workspace }} + run: | + export PATH=$GITHUB_WORKSPACE/clang/bin:$PATH + # export KBUILD_BUILD_USER=${{ github.repository_owner }} + # export KBUILD_BUILD_HOST= + export KBUILD_BUILD_TIMESTAMP=$(date -u -d "@$(git log -1 --format=%at)" +"%a %b %d %H:%M:%S %Z %Y") + make -j$(nproc --all) \ + O=out \ + LLVM=1 \ + LLVM_IAS=1 \ + CC="ccache clang" \ + LD=ld.lld \ + ARCH=arm64 \ + CROSS_COMPILE=aarch64-linux-gnu- \ + CROSS_COMPILE_ARM32=arm-linux-gnueabi- \ + vendor/xiaomi/mi845_defconfig \ + vendor/xiaomi/${{ matrix.device }}.config \ + all + + - name: Show ccache statistics + if: always() + run: ccache -d .ccache -s + + - name: Save ccache + if: always() && matrix.is_primary == true && steps.ccache.outputs.cache-hit != 'true' + uses: actions/cache/save@v6 + with: + path: .ccache + key: ccache-kernel-${{ github.run_id }} + + - name: Create build metadata + if: matrix.is_primary == true + working-directory: kernel + run: | + KERNEL_VER=$(cat out/include/config/kernel.release) + CLANG_VER=$(../clang/bin/clang --version | head -1 | grep -oE 'clang version [0-9.]+' | awk '{print $3}') + MAKE_VER=$(make --version | head -1 | awk '{print $3}') + COMMIT_HASH=$(git log -1 --format=%h) + COMMIT_SUBJECT=$(git log -1 --format=%s) + COMMIT_DATE=$(git log -1 --format=%cs) + + jq -n \ + --arg kv "${KERNEL_VER}" \ + --arg cv "${CLANG_VER}" \ + --arg ci "${{ env.AOSP_CLANG_VERSION }}" \ + --arg mv "${MAKE_VER}" \ + --arg ch "${COMMIT_HASH}" \ + --arg cs "${COMMIT_SUBJECT}" \ + --arg cd "${COMMIT_DATE}" \ + '{ + kernel_version: $kv, + clang_version: $cv, + clang_id: $ci, + make_version: $mv, + commit_hash: $ch, + commit_subject: $cs, + commit_date: $cd + }' > ../build-info.json + + echo "=== Build metadata ===" + cat ../build-info.json + + - name: Upload build metadata + if: matrix.is_primary == true + uses: actions/upload-artifact@v7 + with: + name: build-info.json + path: build-info.json + compression-level: 0 + + - name: Build AnyKernel3 flashable zip + run: | + git clone --depth=1 https://github.com/osm0sis/AnyKernel3.git ak3 + + if [ ! -f kernel/out/arch/arm64/boot/Image.gz-dtb ]; then + echo "Error: Image.gz-dtb not found in build output." + exit 2 + fi + + cp kernel/out/arch/arm64/boot/Image.gz-dtb ak3/ + + if [ -f build-info.json ]; then + KERNEL_VER=$(jq -r '.kernel_version' build-info.json) + COMMIT_HASH=$(jq -r '.commit_hash' build-info.json) + else + KERNEL_VER="unknown" + COMMIT_HASH="unknown" + fi + + cd ak3 + sed -i \ + -e 's/kernel.string=.*/kernel.string=Kernel ${KERNEL_VER} for ${{ matrix.device_name }}/' \ + -e 's/device.name1=.*/device.name1=${{ matrix.device }}/' \ + -e 's/device.name2=.*/device.name2=/' \ + -e 's/device.name3=.*/device.name3=/' \ + -e 's/device.name4=.*/device.name4=/' \ + anykernel.sh + + # Do not use the pattern "^#*BLOCK=.*" since there are several lines containing "BLOCK=". + sed -i -e 's|BLOCK=/dev/block/platform/omap/omap_hsmmc.0/by-name/boot|BLOCK=${{ matrix.boot_block }}|' anykernel.sh + + ZIP_NAME="Anykernel3-${{ matrix.device }}-${KERNEL_VER}-${COMMIT_HASH}.zip" + zip -qr9 "${ZIP_NAME}" . -x "./.git/*" "./.github/*" "./README.md" + + echo "ZIP_NAME=${ZIP_NAME}" >> "$GITHUB_ENV" + + - name: Upload artifact + uses: actions/upload-artifact@v7 + with: + name: kernel-${{ matrix.device }}-ak3 + path: ak3/${{ env.ZIP_NAME }} + compression-level: 0 diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml new file mode 100755 index 000000000000..8815c323c06f --- /dev/null +++ b/.github/workflows/release.yml @@ -0,0 +1,265 @@ +name: Build release kernel + +on: + workflow_dispatch: + +env: + AOSP_TOOLCHAIN_BRANCH: android16 + AOSP_CLANG_VERSION: r547379 + +jobs: + build: + timeout-minutes: 60 + name: Build kernel + permissions: { contents: read } + runs-on: ubuntu-26.04 + strategy: + fail-fast: true + matrix: + include: + - device: beryllium + device_name: "Xiaomi Poco F1" + boot_block: auto + is_primary: true + #- device: dipper + # device_name: "Xiaomi Mi 8" + # boot_block: auto + # is_primary: false + #- device: equuleus + # device_name: "Xiaomi Mi 8 Pro" + # boot_block: auto + # is_primary: false + #- device: perseus + # device_name: "Xiaomi Mi MIX 3" + # boot_block: auto + # is_primary: false + #- device: polaris + # device_name: "Xiaomi Mi MIX 2S" + # boot_block: auto + # is_primary: false + #- device: ursa + # device_name: "Xiaomi Mi 8 Explorer Edition" + # boot_block: auto + # is_primary: false + steps: + - name: Install dependencies + run: | + dependencies=( + ccache + binutils-aarch64-linux-gnu + binutils-arm-linux-gnueabi + make + ) + + sudo apt-get update -y -q + sudo apt-get install -y -q "${dependencies[@]}" --no-install-recommends + + - name: Sync repo + uses: actions/checkout@v7 + with: + path: kernel + fetch-depth: 1 + show-progress: false + + - name: Cache Clang + id: cache-clang + uses: actions/cache/restore@v6 + with: + path: clang + key: clang-${{ env.AOSP_TOOLCHAIN_BRANCH }}-${{ env.AOSP_CLANG_VERSION }} + + - name: Setup Clang + id: download_clang + if: steps.cache-clang.outputs.cache-hit != 'true' + run: | + mkdir -p "clang/" + wget -c -t 10 -O "clang.tar.gz" "https://android.googlesource.com/platform/prebuilts/clang/host/linux-x86/+archive/refs/heads/${{ env.AOSP_TOOLCHAIN_BRANCH }}-release/clang-${{ env.AOSP_CLANG_VERSION }}.tar.gz" + tar -zxf "clang.tar.gz" -C "clang/" + + - name: Save Clang + if: steps.cache-clang.outputs.cache-hit != 'true' && steps.download_clang.outcome == 'success' + uses: actions/cache/save@v6 + with: + path: clang + key: clang-${{ env.AOSP_TOOLCHAIN_BRANCH }}-${{ env.AOSP_CLANG_VERSION }} + + - name: Setup ccache + run: | + mkdir -p .ccache + ccache -M 5G + + - name: Restore ccache + id: ccache + uses: actions/cache/restore@v6 + with: + path: .ccache + key: ccache-kernel-${{ github.run_id }} + restore-keys: | + ccache-kernel- + + - name: Reset ccache statistics + run: | + ccache -d .ccache -z + + - name: Compile kernel + working-directory: kernel + env: + CCACHE_DIR: ${{ github.workspace }}/.ccache + CCACHE_NOHASHDIR: 1 + CCACHE_COMPILERCHECK: content + CCACHE_BASEDIR: ${{ github.workspace }} + run: | + export PATH=$GITHUB_WORKSPACE/clang/bin:$PATH + # export KBUILD_BUILD_USER=${{ github.repository_owner }} + # export KBUILD_BUILD_HOST= + export KBUILD_BUILD_TIMESTAMP=$(date -u -d "@$(git log -1 --format=%at)" +"%a %b %d %H:%M:%S %Z %Y") + make -j$(nproc --all) \ + O=out \ + LLVM=1 \ + LLVM_IAS=1 \ + CC="ccache clang" \ + LD=ld.lld \ + ARCH=arm64 \ + CROSS_COMPILE=aarch64-linux-gnu- \ + CROSS_COMPILE_ARM32=arm-linux-gnueabi- \ + vendor/xiaomi/mi845_defconfig \ + vendor/xiaomi/${{ matrix.device }}.config \ + all + + - name: Show ccache statistics + if: always() + run: ccache -d .ccache -s + + - name: Save ccache + if: always() && matrix.is_primary == true && steps.ccache.outputs.cache-hit != 'true' + uses: actions/cache/save@v6 + with: + path: .ccache + key: ccache-kernel-${{ github.run_id }} + + - name: Create build metadata + if: matrix.is_primary == true + working-directory: kernel + run: | + KERNEL_VER=$(cat out/include/config/kernel.release) + CLANG_VER=$(../clang/bin/clang --version | head -1 | grep -oE 'clang version [0-9.]+' | awk '{print $3}') + MAKE_VER=$(make --version | head -1 | awk '{print $3}') + COMMIT_HASH=$(git log -1 --format=%h) + COMMIT_SUBJECT=$(git log -1 --format=%s) + COMMIT_DATE=$(git log -1 --format=%cs) + + jq -n \ + --arg kv "${KERNEL_VER}" \ + --arg cv "${CLANG_VER}" \ + --arg ci "${{ env.AOSP_CLANG_VERSION }}" \ + --arg mv "${MAKE_VER}" \ + --arg ch "${COMMIT_HASH}" \ + --arg cs "${COMMIT_SUBJECT}" \ + --arg cd "${COMMIT_DATE}" \ + '{ + kernel_version: $kv, + clang_version: $cv, + clang_id: $ci, + make_version: $mv, + commit_hash: $ch, + commit_subject: $cs, + commit_date: $cd + }' > ../build-info.json + + echo "=== Build metadata ===" + cat ../build-info.json + + - name: Upload build metadata + if: matrix.is_primary == true + uses: actions/upload-artifact@v7 + with: + name: build-info.json + path: build-info.json + compression-level: 0 + + - name: Build AnyKernel3 flashable zip + run: | + git clone --depth=1 https://github.com/osm0sis/AnyKernel3.git ak3 + + if [ ! -f kernel/out/arch/arm64/boot/Image.gz-dtb ]; then + echo "Error: Image.gz-dtb not found in build output." + exit 2 + fi + + cp kernel/out/arch/arm64/boot/Image.gz-dtb ak3/ + + if [ -f build-info.json ]; then + KERNEL_VER=$(jq -r '.kernel_version' build-info.json) + COMMIT_HASH=$(jq -r '.commit_hash' build-info.json) + else + KERNEL_VER="unknown" + COMMIT_HASH="unknown" + fi + + cd ak3 + sed -i \ + -e 's/kernel.string=.*/kernel.string=Kernel ${KERNEL_VER} for ${{ matrix.device_name }}/' \ + -e 's/device.name1=.*/device.name1=${{ matrix.device }}/' \ + -e 's/device.name2=.*/device.name2=/' \ + -e 's/device.name3=.*/device.name3=/' \ + -e 's/device.name4=.*/device.name4=/' \ + anykernel.sh + + # Do not use the pattern "^#*BLOCK=.*" since there are several lines containing "BLOCK=". + sed -i -e 's|BLOCK=/dev/block/platform/omap/omap_hsmmc.0/by-name/boot|BLOCK=${{ matrix.boot_block }}|' anykernel.sh + + ZIP_NAME="Anykernel3-${{ matrix.device }}-${KERNEL_VER}-${COMMIT_HASH}.zip" + zip -qr9 "${ZIP_NAME}" . -x "./.git/*" "./.github/*" "./README.md" + + echo "ZIP_NAME=${ZIP_NAME}" >> "$GITHUB_ENV" + + - name: Upload artifact + uses: actions/upload-artifact@v7 + with: + name: kernel-${{ matrix.device }}-ak3 + path: ak3/${{ env.ZIP_NAME }} + compression-level: 0 + + release: + name: Publish release + permissions: { contents: write } + runs-on: ubuntu-26.04 + needs: build + steps: + - name: Download build artifacts + uses: actions/download-artifact@v8 + with: + path: artifacts + pattern: "{kernel-*,build-info.json}" + merge-multiple: true + + - name: Get current time + id: time + run: | + NOW=$(date +%s) + TIME_STR=$(date -u -d "@$NOW" +'%Y%m%d%H%M') + echo "timestamp=$NOW" >> $GITHUB_OUTPUT + echo "time=$TIME_STR" >> $GITHUB_OUTPUT + + - name: Prepare release notes + id: notes + working-directory: artifacts + run: | + RELEASE_BODY=$(jq -r '"**Kernel:** \(.kernel_version)\n**Compiler:** \(.clang_version) (\(.clang_id))\n**Commit:** `\(.commit_hash)` - \(.commit_subject)\n**Date:** \(.commit_date)"' build-info.json) + + { + echo 'body<> "$GITHUB_OUTPUT" + + - name: Create GitHub Release + uses: softprops/action-gh-release@v3 + id: release + with: + tag_name: rel-${{ steps.time.outputs.timestamp }} + name: Kernel build ${{ steps.time.outputs.time }} + prerelease: false + body: ${{ steps.notes.outputs.body }} + files: | + artifacts/*.zip diff --git a/.gitignore b/.gitignore index 72988800c556..27b6456c704e 100644 --- a/.gitignore +++ b/.gitignore @@ -67,6 +67,7 @@ Module.symvers # git files that we don't want to ignore even if they are dot-files # !.gitignore +!.github/ !.mailmap !.cocciconfig