250 líneas de comentario en 151 scripts. Control verificado: el diff no toca NI UNA línea que no empiece por #, y la sintaxis de los 151 pasa. El barrido saltea heredocs y cadenas triples, y el guardián DISPARÓ 3 veces: las tres eran el MOTD que el script escribe DENTRO de la imagen construida — texto del producto, no comentario del script. Se cambiaron aparte y a propósito, que es rebranding, no limpieza. Y el hallazgo caro: casaba contra , que es el TARGET de tracing — o sea el module_path!, o sea el nombre del crate. La etapa 4 lo movió a y el script quedó casando NADA. No fallaba: imprimía cero atribuciones, indistinguible de un log sin problemas. Comprobado con el binario (RUST_LOG=info sobre zlib), no deducido. Ahora acepta las dos, y tiene que seguir aceptándolas porque los logs viejos en disco dicen la vieja. Además 14 rutas de módulo en docs, que el barrido anterior no tocó porque no es frontera de palabra.
103 lines
5.2 KiB
Bash
Executable File
103 lines
5.2 KiB
Bash
Executable File
#!/usr/bin/env sh
|
|
# metal-firmware.sh — inyecta el firmware del WiFi AX201 (y reg.db) en /lib/firmware de un rootfs.
|
|
#
|
|
# El firmware de iwlwifi son BLOBS binarios NO compilables desde fuente (Intel no libera el código); la
|
|
# soberanía de takana (build-from-source) no aplica acá — son datos fijos como el microcódigo de la CPU.
|
|
# Se fijan por contenido (igual que un tarball pinned): se copian de un linux-firmware ya presente y se
|
|
# descomprimen a .ucode plano (el kernel metal NO habilita FW_LOADER_COMPRESS, así evitamos esa dep).
|
|
#
|
|
# Target: Intel Wi-Fi 6 AX201 [8086:a0f0] en TigerLake ⇒ familias QuZ-a0-hr-b0 + cc-a0 (el driver elige
|
|
# la API más alta que soporta) + regulatory.db(+.p7s) que cfg80211 verifica con la clave built-in.
|
|
#
|
|
# Copia además el firmware de i915 (DMC/GuC/HuC) y el de SOF (el DSP de audio de TigerLake). El nombre
|
|
# del script dice «firmware» y no «wifi» a propósito: son las tres familias de blobs que el metal
|
|
# necesita y ninguna se construye desde fuente.
|
|
#
|
|
# Uso: scripts/metal-firmware.sh <rootfs-dir>
|
|
# Vars: FWSRC dir origen del firmware (default /lib/firmware del host)
|
|
#
|
|
# TODO(soberanía): reemplazar FWSRC=host por un pin a un commit de linux-firmware (recipe fetch+extract).
|
|
set -eu
|
|
|
|
DST="${1:?uso: metal-firmware.sh <rootfs-dir>}"
|
|
FWSRC="${FWSRC:-/lib/firmware}"
|
|
OUT="$DST/lib/firmware"
|
|
mkdir -p "$OUT"
|
|
|
|
# patrones de firmware que el AX201 puede pedir (ambas familias, todas las API presentes)
|
|
PATTERNS="iwlwifi-QuZ-a0-hr-b0-*.ucode iwlwifi-cc-a0-*.ucode"
|
|
n=0
|
|
for pat in $PATTERNS; do
|
|
for src in "$FWSRC"/$pat "$FWSRC"/$pat.zst "$FWSRC"/$pat.xz; do
|
|
[ -e "$src" ] || continue
|
|
base=$(basename "$src")
|
|
case "$base" in
|
|
*.zst) dst="$OUT/${base%.zst}"; zstd -q -d -f -o "$dst" "$src" ;;
|
|
*.xz) dst="$OUT/${base%.xz}"; xz -dc "$src" > "$dst" ;;
|
|
*) dst="$OUT/$base"; cp "$src" "$dst" ;;
|
|
esac
|
|
n=$((n+1))
|
|
done
|
|
done
|
|
|
|
# regulatory db (texto firmado; cfg80211 lo carga vía firmware loader y verifica .p7s con clave built-in)
|
|
for f in regulatory.db regulatory.db.p7s; do
|
|
if [ -e "$FWSRC/$f" ]; then cp "$FWSRC/$f" "$OUT/$f"; n=$((n+1)); fi
|
|
done
|
|
|
|
# i915 (panel/GPU TigerLake): DMC (enciende el display tras ExitBootServices) + GuC/HuC. El driver pide
|
|
# versiones EXACTAS por nombre; copiamos TODAS las tgl_* (1.3M) para que encuentre la que su versión usa.
|
|
mkdir -p "$OUT/i915"
|
|
for src in "$FWSRC"/i915/tgl_*.bin "$FWSRC"/i915/tgl_*.bin.zst; do
|
|
[ -e "$src" ] || continue
|
|
base=$(basename "$src")
|
|
case "$base" in
|
|
*.zst) zstd -q -d -f -o "$OUT/i915/${base%.zst}" "$src" ;;
|
|
*.xz) xz -dc "$src" > "$OUT/i915/${base%.xz}" ;;
|
|
*) cp "$src" "$OUT/i915/$base" ;;
|
|
esac
|
|
n=$((n+1))
|
|
done
|
|
|
|
# SOF (Sound Open Firmware) para TigerLake. Intel movió el audio de TGL al DSP: el kernel trae el
|
|
# driver (`SND_SOC_SOF_TIGERLAKE`, encendido en linux-metal) pero **sin estos blobs carga y falla**, y en
|
|
# el laptop no hay sonido aunque ALSA esté. En QEMU no importa: ahí manda la ruta HDA legacy.
|
|
# Es el mismo patrón que i915 con su DMC/GuC — driver de fuente, firmware pineado por contenido.
|
|
#
|
|
# Tres piezas, y las tres hacen falta por motivos distintos:
|
|
# · sof-tgl.ri / sof-tgl-h.ri el firmware del DSP (LP y H). Se copian los DOS porque el driver
|
|
# elige según el SKU y no queremos hornear la suposición. **`cp -L`**: en linux-firmware son
|
|
# SYMLINKS a `intel-signed/`, y un symlink relativo copiado a otro árbol apunta a la nada.
|
|
# · sof-tgl.ldc el diccionario de logs del DSP. No es opcional en la práctica: el driver lo pide al
|
|
# inicializar y, si falta, el firmware arranca sin traza — o sea que el día que algo falle no hay
|
|
# por dónde mirar. 95 KB.
|
|
# · sof-tplg/*.tplg las TOPOLOGÍAS: describen el grafo de audio (qué DAI, cuántos canales, qué
|
|
# códec). El driver pide UNA por nombre, derivado de la máquina, y no se puede saber cuál sin el
|
|
# hardware delante. Se copian las `sof-hda-generic-*` (el caso HDA sobre SOF, que es el del target)
|
|
# y las `sof-tgl-*` — ~2 MB en total. Copiar de más cuesta megas; copiar de menos cuesta un viaje
|
|
# físico al laptop para descubrir qué nombre pidió.
|
|
mkdir -p "$OUT/intel/sof" "$OUT/intel/sof-tplg"
|
|
for src in "$FWSRC"/intel/sof/sof-tgl.ri "$FWSRC"/intel/sof/sof-tgl-h.ri "$FWSRC"/intel/sof/sof-tgl.ldc; do
|
|
[ -e "$src" ] || continue
|
|
cp -L "$src" "$OUT/intel/sof/$(basename "$src")"
|
|
n=$((n+1))
|
|
done
|
|
for src in "$FWSRC"/intel/sof-tplg/sof-hda-generic-*.tplg "$FWSRC"/intel/sof-tplg/sof-tgl-*.tplg; do
|
|
[ -e "$src" ] || continue
|
|
cp -L "$src" "$OUT/intel/sof-tplg/$(basename "$src")"
|
|
n=$((n+1))
|
|
done
|
|
sof_ri=$(ls "$OUT"/intel/sof/*.ri 2>/dev/null | wc -l)
|
|
sof_tplg=$(ls "$OUT"/intel/sof-tplg/*.tplg 2>/dev/null | wc -l)
|
|
if [ "$sof_ri" -eq 0 ]; then
|
|
# Aviso y NO error: el audio del laptop se pierde, pero la imagen sigue booteando y en QEMU suena por
|
|
# HDA legacy. Fallar acá bloquearía builds que no necesitan SOF.
|
|
echo "metal-firmware: ⚠ SIN firmware SOF en $FWSRC/intel/sof — el laptop TigerLake no tendrá audio" >&2
|
|
else
|
|
echo "metal-firmware: SOF = $sof_ri .ri + $sof_tplg topologías"
|
|
fi
|
|
|
|
[ "$n" -gt 0 ] || { echo "metal-firmware: NO encontré firmware AX201 en $FWSRC" >&2; exit 1; }
|
|
echo "metal-firmware: $n blobs → $OUT"
|
|
ls "$OUT" | sed 's/^/ /'
|