Verified rather than taken on description.
`BUILD_RC=$?` is the line immediately after `make BOARD=${DEVICE}`, so nothing
clobbers the status before it is captured, and `exit ${BUILD_RC}` uses the saved
value rather than re-reading `$?` after `echo_c`. `sh -n`, `dash -n` and
`bash -n` all clean. The branch point (`222db9e`) carries a byte-identical
`builder.sh` to master -- md5 `2292222e081fecf876e022c373a943e5` at both -- so
the diff is exactly these twenty lines. 114 checks green.
Agreed on explicit status propagation over `set -e`: the script does enough
unguarded `cp`/`rm`/`cd` that global errexit would change failure behaviour well
beyond this line, and `size-report` keeping its `|| true` is right.
Worth stating plainly for whoever reads this later: this makes the six-step
backoff in `master.yml` live for the first time. A deterministically failing
board -- a rootfs that no longer fits NOR, say -- will now be rebuilt seven times
across roughly 38 minutes of sleeps before the job goes red, where previously it
went green instantly. That is the correct behaviour and the point of the change,
but it is a real shift in what a broken nightly costs, and if it proves
expensive the fix is to make the retry discriminate transient failures from
deterministic ones, not to go back to a script that cannot fail.
187 lines
6.5 KiB
Bash
Executable File
187 lines
6.5 KiB
Bash
Executable File
#!/bin/bash
|
|
#
|
|
# OpenIPC | version 2023.11.30
|
|
|
|
# Autoupdate BUILDER repo
|
|
# Remove old building folder (for full rebuild)
|
|
# Download OpenIPC repo
|
|
# Copy files from Device Overlay
|
|
# Build Firmware
|
|
# Copy Kernel and Rootfs to Archive
|
|
# Copy Kernel and Rootfs to TFTP server
|
|
|
|
DEVICE="$1"
|
|
BUILDER_DIR=$(pwd)
|
|
FIRMWARE_DIR="${BUILDER_DIR}/openipc"
|
|
TIMESTAMP=$(date +"%Y%m%d%H%M")
|
|
VERSION=$(stat -c"%Y" $0)
|
|
|
|
echo_c() {
|
|
# 30 grey, 31 red, 32 green, 33 yellow, 34 blue, 35 magenta, 36 cyan, 37 white
|
|
t="\e[1;$1m$2\e[0m" || t="$2"
|
|
echo -e "$t"
|
|
}
|
|
|
|
autoup_rootfs() {
|
|
DT=$(date +"%y.%m.%d")
|
|
OPENIPC_VER=$(echo OpenIPC v${DT:0:1}.${DT:1})
|
|
SOC=$(echo ${DEVICE} | cut -d_ -f1)
|
|
|
|
echo_c 34 "\nDownloading u-boot created by OpenIPC"
|
|
curl --location --output ./output/images/u-boot-${SOC}-universal.bin \
|
|
https://github.com/OpenIPC/firmware/releases/download/latest/u-boot-${SOC}-universal.bin
|
|
|
|
echo_c 34 "\nMaking autoupdate u-boot image"
|
|
./output/host/bin/mkimage -A arm -O linux -T firmware -n "$OPENIPC_VER" \
|
|
-a 0x0 -e 0x50000 -d ./output/images/u-boot-${SOC}-universal.bin \
|
|
./output/images/autoupdate-uboot.img
|
|
|
|
echo_c 34 "\nMaking autoupdate kernel image"
|
|
./output/host/bin/mkimage -A arm -O linux -T kernel -C none -n "$OPENIPC_VER" \
|
|
-a 0x50000 -e 0x250000 -d ./output/images/uImage.${SOC} \
|
|
./output/images/autoupdate-kernel.img
|
|
|
|
echo_c 34 "\nMaking autoupdate rootfs image"
|
|
./output/host/bin/mkimage -A arm -O linux -T filesystem -n "$OPENIPC_VER" \
|
|
-a 0x250000 -e 0x750000 -d ./output/images/rootfs.squashfs.${SOC} \
|
|
./output/images/autoupdate-rootfs.img
|
|
}
|
|
|
|
copy_to_archive() {
|
|
echo_c 32 "Copying files to local archive"
|
|
mkdir -p "${BUILDER_DIR}/archive/${DEVICE}/${TIMESTAMP}"
|
|
cp -a \
|
|
${FIRMWARE_DIR}/output/images/rootfs.squashfs.* \
|
|
${FIRMWARE_DIR}/output/images/uImage.* \
|
|
${FIRMWARE_DIR}/output/images/*.tar \
|
|
${FIRMWARE_DIR}/output/images/openipc.*.tgz \
|
|
${BUILDER_DIR}/archive/${DEVICE}/${TIMESTAMP}
|
|
|
|
cp -a ${FIRMWARE_DIR}/output/images/sizes.*.json \
|
|
${BUILDER_DIR}/archive/${DEVICE}/${TIMESTAMP} 2>/dev/null || true
|
|
|
|
if [ -f "${FIRMWARE_DIR}/output/images/autoupdate-kernel.img" ]; then
|
|
cp -a ${FIRMWARE_DIR}/output/images/autoupdate* ${BUILDER_DIR}/archive/${DEVICE}/${TIMESTAMP}
|
|
fi
|
|
|
|
echo_c 35 "\nAssembled firmware available in:"
|
|
tree -C "${BUILDER_DIR}/archive/${DEVICE}/${TIMESTAMP}"
|
|
|
|
if $(echo ${DEVICE} | grep -q hi3518ev200_lite); then
|
|
autoup_rootfs
|
|
fi
|
|
}
|
|
|
|
copy_to_tftp() {
|
|
echo_c 32 "\nCopying files to a TFTP server using SCP protocol"
|
|
scp -r \
|
|
${FIRMWARE_DIR}/output/images/rootfs.squashfs.* \
|
|
${FIRMWARE_DIR}/output/images/uImage.* \
|
|
${FIRMWARE_DIR}/output/images/openipc.*.tgz \
|
|
${TFTP_STORAGE}
|
|
|
|
if [ -f "${FIRMWARE_DIR}/output/images/autoupdate-kernel.img" ]; then
|
|
scp -r ${FIRMWARE_DIR}/output/images/autoupdate* ${TFTP_STORAGE}
|
|
fi
|
|
}
|
|
|
|
select_device() {
|
|
AVAILABLE_DEVICES=$(find devices -name *_defconfig | sort | cut -d/ -f5)
|
|
cmd="whiptail --title \"Available devices\" --menu \"Please select a device from the list below:\" 20 70 12"
|
|
for p in ${AVAILABLE_DEVICES//_defconfig}; do cmd="${cmd} \"$p\" \"\""; done
|
|
DEVICE=$(eval "${cmd} 3>&1 1>&2 2>&3")
|
|
if [ $? != 0 ]; then
|
|
echo_c 31 "Cancelled."
|
|
exit 1
|
|
fi
|
|
}
|
|
|
|
copy_extra_packages() {
|
|
extra_package=${BUILDER_DIR}/package
|
|
firmware_package=${FIRMWARE_DIR}/general/package
|
|
cp -afv $extra_package/* $firmware_package
|
|
package_list_file=$firmware_package/Config.in
|
|
for f in "$extra_package"/*
|
|
do
|
|
package_name=$(basename $f)
|
|
if ! grep -Fq "$package_name" $package_list_file
|
|
then
|
|
printf 'source "$BR2_EXTERNAL_GENERAL_PATH/package/%s/Config.in"\n' $package_name >> $package_list_file
|
|
fi
|
|
done
|
|
}
|
|
|
|
echo_c 37 "Experimental system for building OpenIPC firmware for known devices"
|
|
echo_c 30 "https://openipc.org/"
|
|
echo_c 30 "Version: ${VERSION}"
|
|
|
|
while [ -z "${DEVICE}" ]; do select_device; done
|
|
|
|
echo_c 31 "\nStarting a device for ${DEVICE}"
|
|
ITEM=$(find devices -name ${DEVICE}_defconfig | cut -d/ -f1,2)
|
|
tree -C "${ITEM}"
|
|
|
|
sleep 3
|
|
|
|
echo_c 33 "\nUpdating Builder"
|
|
git pull
|
|
|
|
rm -rf openipc
|
|
# OPENIPC_FW_REV pins firmware to a specific ref (branch, tag, or SHA) for
|
|
# cross-repo bisect of size/regression issues — set by build-one.yml's
|
|
# firmware_ref input. When unset, clones HEAD of master as before.
|
|
if [ ! -d "$FIRMWARE_DIR" ]; then
|
|
if [ -n "$OPENIPC_FW_REV" ]; then
|
|
echo_c 33 "\nDownloading Firmware @ ${OPENIPC_FW_REV}"
|
|
git clone https://github.com/OpenIPC/firmware.git "$FIRMWARE_DIR"
|
|
git -C "$FIRMWARE_DIR" checkout "$OPENIPC_FW_REV"
|
|
else
|
|
echo_c 33 "\nDownloading Firmware"
|
|
git clone --depth=1 https://github.com/OpenIPC/firmware.git "$FIRMWARE_DIR"
|
|
fi
|
|
cd "$FIRMWARE_DIR"
|
|
else
|
|
echo_c 33 "\nUpdating Firmware"
|
|
cd "$FIRMWARE_DIR"
|
|
# git reset HEAD --hard
|
|
# git pull --rebase
|
|
fi
|
|
|
|
echo_c 33 "\nCopying extra packages"
|
|
copy_extra_packages
|
|
|
|
echo_c 33 "\nCopying device files"
|
|
cp -afv ${BUILDER_DIR}/${ITEM}/* ${FIRMWARE_DIR}
|
|
|
|
echo_c 33 "\nBuilding the device"
|
|
# Propagate make's status. Without this the script ALWAYS exits 0: the result is
|
|
# discarded, copy_to_archive then runs over an empty output/images and still
|
|
# prints "Assembled firmware available in:", and the caller sees success over an
|
|
# empty directory.
|
|
#
|
|
# The expensive consequence is in CI. master.yml calls this inside a retry loop
|
|
# written as `bash builder.sh ${NAME} && break`, wrapped in a six-step backoff
|
|
# meant to absorb transient toolchain and CDN flakes. A script that cannot fail
|
|
# breaks on the first attempt, so the budget never retried anything and the
|
|
# `exit 1` after the loop was unreachable — a genuinely failed build reported
|
|
# green instead of being re-attempted.
|
|
#
|
|
# Explicit rather than `set -e` at the top: this script does a lot of unguarded
|
|
# cp/rm/cd, and enabling errexit globally would change failure behaviour well
|
|
# beyond this line.
|
|
make BOARD=${DEVICE}
|
|
BUILD_RC=$?
|
|
if [ ${BUILD_RC} -ne 0 ]; then
|
|
echo_c 31 "\nBuild FAILED (make exited ${BUILD_RC}) - not archiving"
|
|
exit ${BUILD_RC}
|
|
fi
|
|
|
|
# Best-effort: emit per-package/per-kernel-module size JSON next to the .tgz.
|
|
# Target lives in firmware's Makefile (PR #2166); ignore failure so legacy
|
|
# pinned firmware refs without the target don't sink the build.
|
|
make BOARD=${DEVICE} size-report || true
|
|
|
|
copy_to_archive
|
|
echo_c 35 "\nDone"
|
|
cd "$BUILDER_DIR"
|