Los llamadores EJECUTABLES: scripts/ (incluida toda la granja), los runbooks y CLAUDE.md. Seguro porque la 3a ya garantiza que el worker emite los dos binarios, y porque en farm-lab-sync.sh el cargo build remoto precede a la invocación remota en el mismo script. Verificado: sintaxis de los 49 (bash -n / py_compile — ojo que why-differs-barrido.sh es Python con extensión .sh) y `takana hash` devuelve hash real sobre el store. NO se toca en esta etapa, a propósito: - La variable de entorno HAMMER=. Es interfaz de los scripts entre sí y hay llamadores que la fijan; renombrarla va con la etapa 4. - docs/evidencia/ y los HANDOFF: son REGISTRO de lo que se corrió ese día. Reescribir un comando dentro de una evidencia la falsifica. - docs/state/: es generado, se regenera solo. - Los ADR y los docs de diseño: texto, y `hammer` sigue funcionando. Van con la etapa 5, que es la de churn de texto.
45 lines
2.8 KiB
Bash
45 lines
2.8 KiB
Bash
# pid1-desde-store.sh — helper compartido por los scripts de imagen: poner en el rootfs fundido el
|
|
# arje-zero SELLADO, no el que venga arrastrado del directorio base.
|
|
#
|
|
# ── POR QUÉ EXISTE ──────────────────────────────────────────────────────────────────────────────
|
|
# `work/metal-rootfs` se armó a mano en la campaña de metal y quedó CONGELADO: su `arje-zero` era del
|
|
# 2026-06-19. Nadie lo regeneraba al re-sellar la receta, así que cada imagen de escritorio —GNOME,
|
|
# KDE, metal, dual— arrancaba con un PID1 de hace mes y medio **sin que nada lo dijera**.
|
|
#
|
|
# Así se comió un fix real: el `identity mismatch` del bus del fractal estaba arreglado río arriba
|
|
# (tawasuyu ce96cfa8d) y la VM seguía imprimiendo el mensaje viejo, porque el binario de la imagen no
|
|
# venía de la receta. Se pasaron sesiones creyendo que era un bug nuestro por arreglar.
|
|
#
|
|
# El síntoma es engañoso porque el directorio base es LEGÍTIMO para todo lo demás —busybox, firmware,
|
|
# el kernel EFI-stub, la estructura de /etc—: sólo la pieza que TAMBIÉN es receta se queda atrás, y
|
|
# justo esa es PID1. De ahí la regla:
|
|
#
|
|
# **si algo del rootfs tiene receta, la imagen lo toma del artefacto sellado, no de la copia
|
|
# congelada.**
|
|
#
|
|
# El artefacto se elige por `hammer hash` sobre la receta —el que corresponde a la receta de HOY—, no
|
|
# por el más reciente del store: con dos artefactos del mismo paquete conviviendo, la fecha miente.
|
|
# Mismo criterio que ya usaban los inyectores de arje-logind-compat y arje-polkit-compat.
|
|
#
|
|
# ABORTA si no hay artefacto. Es deliberado: seguir con el PID1 congelado es exactamente el modo de
|
|
# falla que este helper existe para cerrar, y un aviso que no corta se lee como ruido.
|
|
#
|
|
# Uso: . scripts/lib/pid1-desde-store.sh ; inyectar_pid1 "$MERGED" "$BASE"
|
|
# Var: AZ=<dir del store> fuerza un artefacto concreto (diagnóstico).
|
|
|
|
inyectar_pid1() {
|
|
local merged="$1" base="${2:-}" az
|
|
echo "==> PID1: arje-zero desde el store${base:+ (no desde $base)}"
|
|
az="${AZ:-store/$(./target/release/takana --store store hash recipes/arje-zero.toml 2>/dev/null | tail -1 | sed 's/^b3://')-arje-zero}"
|
|
if [ -d "$az" ] && [ -x "$az/usr/bin/arje-zero" ]; then
|
|
install -Dm755 "$az"/usr/bin/arje-zero "$merged"/usr/bin/arje-zero
|
|
local viejo=""
|
|
[ -n "$base" ] && viejo=$(stat -c '%y' "$base"/usr/bin/arje-zero 2>/dev/null | cut -d' ' -f1)
|
|
echo " ✓ $(basename "$az" | cut -c1-12)${viejo:+ (el de $base era de $viejo)}"
|
|
else
|
|
echo " ✗ falta arje-zero sellado en store/ — la imagen usaría el PID1 CONGELADO${base:+ de $base}" >&2
|
|
echo " construílo: ./target/release/takana build recipes/arje-zero.toml --store store" >&2
|
|
return 1
|
|
fi
|
|
}
|