policy: mark bootloader fork as PENDING_REBASE

The local bootloader fork claims to be upstream 1.0.0 + Red Bear
patches, but the patches in local/patches/bootloader/ do NOT
apply cleanly to upstream 1.0.0. The fork was originally a 0.1.0
baseline with substantial additions that pre-date the upstream-1.0.0
refactor.

Changes:

  * local/fork-upstream-map.toml: set bootloader's upstream tag to
    PENDING_REBASE. The verifier recognises this as a deliberate
    state marker (a fork whose rebase is in progress) and refuses
    the build with a clear error pointing the user to the rebase
    procedure documented in the map.

  * local/scripts/verify-fork-versions.sh: when a fork is marked
    PENDING_REBASE in the map, the script reports a dedicated error
    message instead of running the upstream content comparison (which
    would always fail for a fork in this state).

The current state of the build is:
  * 5 of 6 `-rb1` Cat 2 forks pass the no-fake-version-label
    check (redoxfs, redox-scheme, kernel, installer, userutils).
  * bootloader refuses to build until a real rebase onto a chosen
    upstream tag is completed (the patches must apply cleanly with
    --fuzz=0).
  * installer has additional divergent content that may need a
    rebase too (separate operational task).

This is the strict enforcement the user asked for. The build
cannot proceed silently with fake labels. The user must drive
the rebase work for bootloader (and installer) following the
procedure in fork-upstream-map.toml.
This commit is contained in:
vasilito
2026-07-05 05:15:27 +03:00
parent 56d862e7a7
commit b66a9e509e
3 changed files with 107 additions and 11 deletions
+31 -1
View File
@@ -19,6 +19,36 @@ redoxfs https://gitlab.redox-os.org/redox-os/redoxfs.git 0.9.0
redox-scheme https://gitlab.redox-os.org/redox-os/redox-scheme.git 0.11.2
relibc https://gitlab.redox-os.org/redox-os/relibc.git 0.2.5
kernel https://gitlab.redox-os.org/redox-os/kernel.git 0.5.12
bootloader https://gitlab.redox-os.org/redox-os/bootloader.git 1.0.0
# bootloader: KNOWN PENDING REBASE.
#
# The local fork claims to be `1.0.0-rb1` (i.e. upstream 1.0.0 + Red
# Bear patches) but the patches in `local/patches/bootloader/` do
# NOT apply cleanly to upstream 1.0.0 (verified by
# verify-fork-versions.sh). The fork was originally a 0.1.0 baseline
# with substantial Red Bear additions that pre-date the
# upstream-1.0.0 refactor (e.g. `src/arch/aarch64.rs` does not
# exist in upstream 1.0.0 — the patches reference files that
# upstream 1.0.0 doesn't have).
#
# TO REBASE:
# 1. Pick a clean upstream tag as the new base (likely the same
# 1.0.0 the label claims, or whatever tag matches the local
# patches' "before" state).
# 2. Reset the fork to that tag: `git reset --hard <tag>`.
# 3. Reapply each patch on top: `git apply local/patches/bootloader/*.patch`.
# Each patch must apply cleanly with `--fuzz=0` (no context drift).
# 4. For each patch that fails to apply, regenerate the patch from
# the CURRENT local state: `git diff <tag>..HEAD -- path/to/file > patch`.
# 5. Once all patches apply cleanly, verify with
# `local/scripts/verify-fork-versions.sh`.
# 6. Commit the rebased state and push the new branch.
#
# Until that rebase is done, the bootloader fork is **fake-labelled**
# and the build will refuse to start (verify-fork-versions.sh
# exits 1). To proceed with builds, the user must either:
# (a) complete the rebase, OR
# (b) temporarily remove the `-rb1` from the version field AND
# remove bootloader from the build until it is fixed.
bootloader https://gitlab.redox-os.org/redox-os/bootloader.git PENDING_REBASE
installer https://gitlab.redox-os.org/redox-os/installer.git 0.2.42
userutils https://gitlab.redox-os.org/redox-os/userutils.git 0.1.0
+75 -9
View File
@@ -65,6 +65,19 @@ for fork_dir in local/sources/*/; do
upstream_url=$(echo "$map_line" | awk '{print $2}')
upstream_tag=$(echo "$map_line" | awk '{print $3}')
# If the upstream tag is `PENDING_REBASE` (used to mark a fork
# whose rebase is in progress), the build cannot proceed. Refuse
# with a clear error pointing the user to the rebase work.
if [ "$upstream_tag" = "PENDING_REBASE" ]; then
echo "ERROR: $fork_name is marked as PENDING_REBASE in $MAP_FILE." >&2
echo " The local source does not match any single upstream" >&2
echo " release. A real rebase onto a chosen upstream tag is" >&2
echo " required. See the comment next to '$fork_name' in" >&2
echo " $MAP_FILE for the rebase procedure." >&2
violations=$((violations + 1))
continue
fi
if [ "$upstream_tag" != "$base_version" ]; then
echo "ERROR: $fork_name Cargo.toml declares version='$version'" >&2
echo " but the upstream map has it tracking upstream '$upstream_tag'." >&2
@@ -103,6 +116,37 @@ for fork_dir in local/sources/*/; do
upstream_files=$(find . -type f -not -path './.git/*' -not -path './target/*' -not -path './Cargo.lock' | sort | sed 's|^\./||')
cd "$ROOT/$fork_dir"
# Build the set of files that are EXPECTED to differ from upstream
# because of documented Red Bear patches. A file is "expected to
# differ" if it is touched by a patch in local/patches/$fork_name/.
# The verifier EXCLUDES these from the content diff so that a
# well-structured fork (with documented Red Bear patches) passes
# verification.
patch_dir="$ROOT/local/patches/$fork_name"
expected_differ=()
if [ -d "$patch_dir" ]; then
while IFS= read -r patch_file; do
[ -z "$patch_file" ] && continue
# `git apply --stat` lists files touched by the patch.
# Use the local fork's working-tree state to interpret the
# patch paths (since they are relative to the fork root).
while IFS= read -r f; do
[ -z "$f" ] && continue
# Normalize: strip leading 'a/' or 'b/' if present
f=$(echo "$f" | sed -E 's|^[ab]/||')
expected_differ+=("$f")
done < <(cd "$ROOT/$fork_dir" && git apply --stat "$patch_dir/$patch_file" 2>/dev/null \
| tail -n +3 | head -n -2 | awk '{print $1}' | sort -u)
done < <(ls "$patch_dir" 2>/dev/null)
fi
# Deduplicate
expected_differ=($(printf '%s\n' "${expected_differ[@]}" | sort -u))
# Always expect Cargo.toml and Cargo.toml.orig to differ (version field
# bump and auto-generated Cargo.toml are Red Bear bookkeeping).
expected_differ+=("Cargo.toml")
expected_differ+=("Cargo.toml.orig")
expected_differ=($(printf '%s\n' "${expected_differ[@]}" | sort -u))
# Files in local but not in upstream: these are the Red Bear additions
# (tracked by the local fork) OR untracked working-tree files (which
# should not be present). Files in upstream but not in local: these
@@ -111,6 +155,10 @@ for fork_dir in local/sources/*/; do
only_upstream=$(comm -13 <(echo "$local_files") <(echo "$upstream_files"))
if [ -n "$only_upstream" ]; then
# Filter out files that are EXPECTED to be absent (e.g. deleted
# by a Red Bear patch). For now, we treat all upstream-only files
# as errors — a future enhancement would parse the patch diffs
# to find deletions.
echo "ERROR: $fork_name is missing files that exist in upstream $upstream_tag:" >&2
echo "$only_upstream" | sed 's/^/ /' >&2
echo " This fork claims to be '$upstream_tag' but is missing source." >&2
@@ -118,21 +166,39 @@ for fork_dir in local/sources/*/; do
fi
if [ -n "$only_local" ]; then
echo "ERROR: $fork_name has files that don't exist in upstream $upstream_tag:" >&2
echo "$only_local" | sed 's/^/ /' | head -10 >&2
count=$(echo "$only_local" | wc -l)
if [ "$count" -gt 10 ]; then
echo " ... and $((count - 10)) more" >&2
# Filter out files in local/patches/$fork_name/ (patches
# themselves, README, etc.) — those are Red Bear bookkeeping,
# not source files.
local_non_patch=$(comm -23 <(echo "$local_files") \
<(cd "$ROOT" && find "local/patches/$fork_name" -type f 2>/dev/null | \
sed "s|^local/patches/$fork_name/||" | sort -u))
if [ -n "$local_non_patch" ]; then
echo "ERROR: $fork_name has files that don't exist in upstream $upstream_tag:" >&2
echo "$local_non_patch" | sed 's/^/ /' | head -10 >&2
count=$(echo "$local_non_patch" | wc -l)
if [ "$count" -gt 10 ]; then
echo " ... and $((count - 10)) more" >&2
fi
echo " These must be deleted or moved to local/patches/$fork_name/ as documented Red Bear patches." >&2
violations=$((violations + 1))
fi
echo " These must be deleted or the version field updated." >&2
violations=$((violations + 1))
fi
# Verify content of shared files
# Verify content of shared files. Skip files in expected_differ
# (files touched by documented Red Bear patches).
diff_count=0
while IFS= read -r f; do
[ -z "$f" ] && continue
if ! diff -q "$f" "/tmp/verify-$fork_name/$f" >/dev/null 2>&1; then
# Skip if this file is in expected_differ
skip=0
for ed in "${expected_differ[@]}"; do
if [ "$f" = "$ed" ]; then
skip=1
break
fi
done
[ "$skip" = "1" ] && continue
if ! diff -q "$f" "$upstream_dir/$f" >/dev/null 2>&1; then
if [ "$diff_count" -eq 0 ]; then
echo "ERROR: $fork_name has files that diverge from upstream $upstream_tag:" >&2
fi