aboutsummaryrefslogtreecommitdiffci
path: root/build.sh
diff refs
from: back
to: back
| flip
diff options
context:
space:
mode:
Diffstat (limited to 'build.sh')
-rwxr-xr-xbuild.sh101
1 files changed, 101 insertions, 0 deletions
diff --git a/build.sh b/build.sh
new file mode 100755
index 0000000..7e32f3b
--- /dev/null
+++ b/build.sh
@@ -0,0 +1,101 @@
+#!/usr/bin/env bash
+#
+# Rebuild Fedora's libcamera with this board's patches on top.
+#
+# libcamera has no plugin mechanism for CameraSensorHelper: the per-sensor gain
+# models are compiled into libcamera.so, so teaching the software ISP about the
+# Surface Pro 12"'s front sensor means shipping a rebuilt package. The patches
+# in patches/ are held against Fedora's source RPM rather than an upstream git
+# checkout, so the result stays a drop-in replacement for the distribution
+# package -- same name, same subpackages, same soname.
+#
+# Usage: ./build.sh [-o OUTPUT_DIR] [-w WORK_DIR] [-n]
+#
+# -o where the built binary RPMs are copied (default: ./RPMS)
+# -w scratch directory, reused between runs (default: ./.libcamera-build)
+# -n resolve only: print the binary RPM file names the build would produce,
+# one per line, and exit without building. Lets a caller check whether
+# the packages are already published before paying for a build.
+#
+# Environment:
+#
+# RELEASE_SUFFIX what to append to Fedora's release (default: sp12in1)
+
+set -euo pipefail
+
+script_dir=$(cd -- "$(dirname -- "${BASH_SOURCE[0]}")" && pwd)
+patch_dir="${script_dir}/patches"
+suffix=${RELEASE_SUFFIX:-sp12in1}
+
+output_dir="$(pwd)/RPMS"
+work_dir="$(pwd)/.libcamera-build"
+resolve_only=false
+
+while getopts ':o:w:nh' opt; do
+ case "${opt}" in
+ o) output_dir=${OPTARG} ;;
+ w) work_dir=${OPTARG} ;;
+ n) resolve_only=true ;;
+ h) sed -n '2,30p' "${BASH_SOURCE[0]}"; exit 0 ;;
+ *) echo "unknown option -${OPTARG}" >&2; exit 2 ;;
+ esac
+done
+
+topdir="${work_dir}/rpmbuild"
+spec="${topdir}/SPECS/libcamera.spec"
+
+if [[ ! -f ${spec} ]]; then
+ rm -rf "${work_dir}"
+ mkdir -p "${work_dir}" "${topdir}"/{BUILD,BUILDROOT,RPMS,SOURCES,SPECS,SRPMS}
+
+ ( cd "${work_dir}" && dnf download --source libcamera )
+ srpm=$(echo "${work_dir}"/libcamera-*.src.rpm)
+ [[ -f ${srpm} ]] || { echo "no libcamera source RPM was downloaded" >&2; exit 1; }
+ rpm --define "_topdir ${topdir}" -i "${srpm}"
+
+ shopt -s nullglob
+ patches=("${patch_dir}"/*.patch)
+ shopt -u nullglob
+ [[ ${#patches[@]} -gt 0 ]] || { echo "no patches in ${patch_dir}" >&2; exit 1; }
+
+ # The spec uses %autosetup -p1, so a PatchNN: line is the whole of it --
+ # nothing has to call %patch. Number them after the last one Fedora ships.
+ last_num=$(grep -oE '^Patch[0-9]+:' "${spec}" | grep -oE '[0-9]+' | sort -n | tail -1)
+ last_num=${last_num:-0}
+ last_line=$(grep -nE '^Patch[0-9]+:' "${spec}" | tail -1 | cut -d: -f1)
+ [[ -n ${last_line} ]] || { echo "no Patch lines in ${spec} to append after" >&2; exit 1; }
+
+ insert="${work_dir}/patch-lines"
+ : > "${insert}"
+ for patch in "${patches[@]}"; do
+ cp "${patch}" "${topdir}/SOURCES/"
+ last_num=$((10#${last_num} + 1))
+ printf 'Patch%02d: %s\n' "${last_num}" "$(basename "${patch}")" >> "${insert}"
+ done
+ sed -i "${last_line}r ${insert}" "${spec}"
+
+ sed -i -E "0,/^Release:/s/^(Release:[[:space:]]*[^%]*)(%\{\?dist\})/\1.${suffix}\2/" "${spec}"
+ grep -qE "^Release:.*\.${suffix}%\{\?dist\}" "${spec}" || {
+ echo "failed to add the .${suffix} release suffix to ${spec}" >&2
+ exit 1
+ }
+fi
+
+mapfile -t rpm_files < <(rpmspec -q --queryformat '%{NAME}-%{VERSION}-%{RELEASE}.%{ARCH}.rpm\n' "${spec}")
+[[ ${#rpm_files[@]} -gt 0 ]] || { echo "rpmspec -q produced no packages" >&2; exit 1; }
+
+if [[ ${resolve_only} == true ]]; then
+ printf '%s\n' "${rpm_files[@]}"
+ exit 0
+fi
+
+dnf --assumeyes builddep "${spec}"
+rpmbuild --define "_topdir ${topdir}" -bb "${spec}"
+
+mkdir -p "${output_dir}"
+for rpm_file in "${rpm_files[@]}"; do
+ built=$(find "${topdir}/RPMS" -type f -name "${rpm_file}" -print -quit)
+ [[ -n ${built} ]] || { echo "rpmbuild did not produce ${rpm_file}" >&2; exit 1; }
+ cp "${built}" "${output_dir}/"
+ echo "${output_dir}/${rpm_file}"
+done