Commit Graph
2 Commits
Author SHA1 Message Date
e7b9c0c8bf feat(runtime): spec 17 — los pesos se cobran como en la Pi 5, medidos por Laurha en el banco de referencia
Los 23 weights de spec 16, certificados por Laurha en el santuario de la rp1 (origin-banco):
- Núcleo 3 aislado, governor performance a 2,4 GHz, CI parada, 45-49 °C.
- frame-omni-bencher 0.15.0 sobre el wasm 40cb5a1d de 3cd1068.
- 5 procesos por pallet; se cobra el MÁXIMO con scripts/bench/max-de-n.py, porque procesos
  idénticos se separan hasta un 35 %.
- Evidencia: ~/laurha-work/banco/spec16-20261024-1631 en la rp1 (SHA256SUMS d930c5e1).
- Su perfil va en la cabecera de cada weights.rs.

Antes de cobrarlos:
- Mismos accesos a storage: el esqueleto de los 5 ficheros y sus reads/writes son idénticos a
  los de main.
- Lo que Laurha pidió mirar (cast_vote, finalize_proposal y veto_proposal, mucho más altos que
  en RV12) es esperable. Contra los interinos del Mac todos caen en la banda Pi/Mac de 2,5-3,9×:
  es trabajo nuevo de RV15/RV16 en una CPU unas 3 veces más lenta.
- Destacan los tres que verifican Ed25519 en WASM (attest_asset, register_agent_did,
  rotate_agent_key), con unas 6 veces: la criptografía pura sufre más en la Cortex-A76.
- Lo cobrado sube menos que la ejecución, entre +4 % (set_tier_profile) y +56 %
  (rotate_agent_key), porque las lecturas y escrituras de storage no cambian.
- spec_version 16 → 17, porque cambian las fees. transaction_version no cambia: ninguna llamada
  cambia su codificación.

Ensayado en la rp1 (aarch64) sobre un nodo efímero aparte, antes de la testnet de la casa, con
scripts/e2e/upgrade_en_vivo.py (nuevo):
- sudo(set_code) → CodeUpdated + Sudid Ok;
- spec 17 y LastRuntimeUpgrade sube;
- una firma con la spec vieja → «bad signature»; con la nueva, ExtrinsicSuccess;
- la finalidad pasa del bloque del upgrade.
Es la primera vez que el ejecutor ARM compila y corre un runtime nuevo.

Revisión adversarial (nivel 1 de la directiva), antes de tocar la red, con orden de tumbarlo:
no pudo. Los seis puntos aguantan:
- ningún storage ni codificación cambia, y transaction_version no debe subir;
- el más pesado (veto_proposal) cobra 1,9 ms, 344 veces por debajo del máximo por extrinsic;
- los weights.rs tienen la misma estructura y el impl () coincide;
- ninguna fee, subsidio ni test depende del valor de forma que se rompa.

scripts/rp1 (operación del nodo, medido en 23 h con los valores por defecto):
- 430 MB de WAL de RocksDB retenidos para 15 MB de datos, y el RSS subiendo de 200 a 340 MB:
  --db-cache 128. Al reiniciar, 449 → 21 MB.
- El log, de 7 líneas por bloque a ~2 (txpool, sc_basic_authorship y aura en warn; ojo: las
  líneas de autoría usan el target del módulo, no «basic-authorship»), de 16 MB/día a unos 3.
- Modo append, y medir.sh lo rota al pasar de 32 MB.

Co-Authored-By: Laurha <laurha@origin>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-25 12:33:38 -05:00
CharonandClaude Opus 5.5 22bab19932 feat(rp1): la cadena corre en la Pi 5 de la casa — binario aarch64, despliegue sin root y medida continua
David, 24-oct: «lo que podamos hacer en la rp1 hagamoslo no esperemos la VPS porfavor». Y ese
mismo día, por Ergon: la rp1 aloja el servidor de arranque de la red.

scripts/rp1/:
- construir-aarch64.sh + Dockerfile.aarch64: origin-chain-node release, con el WASM real, para
  linux/aarch64 en el Mac.
  - Imagen bookworm (glibc 2.36; la rp1 tiene 2.41).
  - Target en un volumen de Docker: la VM no ve el disco externo de compilación si se montó
    después de arrancar Docker, y reiniciarla tiraría los contenedores de otras hermanas.
  - Copia el binario con docker cp y avisa de cómo borrar el volumen.
- desplegar.sh: copia el binario con su sha256 (y deja el anterior para volver atrás), copia
  arrancar.sh y medir.sh, e instala tres líneas en el crontab del usuario: @reboot, vigilante
  cada 5 min y medida cada 5 min. Sin root y sin systemd.
- arrancar.sh: idempotente.
  - taskset -c 0-2: el nodo nunca toca el núcleo 3, el santuario de origin-banco de Laurha.
  - nice 10 + ionice 7: la CI de la casa va primero.
  - RPC sólo en 127.0.0.1; P2P en el 30333.
  - Cadena dev con Alice: es la testnet de la casa, con llaves públicas de desarrollo; ningún
    valor real.
- medir.sh: una fila CSV cada 5 min con best, finalizado, pares, RSS, CPU, MB de datos, load,
  temperatura y estado de la CI.

scripts/bench/max-de-n.py: funde N weights.rs del mismo pallet cobrando el MÁXIMO de cada
coeficiente.
- Por qué: Laurha midió el 24-oct en su santuario que 8 procesos idénticos de frame-omni-bencher
  separan el base weight hasta un 66 %.
- Se niega si los esqueletos difieren (otra lista de extrinsics o de storage) o si los conteos
  de reads/writes no coinciden. Avisa si N < 5.
- Controles: tres copias idénticas salen idénticas byte a byte; el máximo cae sólo donde se
  subió; un conteo de reads distinto se rechaza; un extrinsic renombrado se rechaza.

firmar_como_wallet: modo cuenta "<frase>" [//derivación], que da la llave sr25519 y la SS58 que
verá un wallet Substrate. Son los vectores para la migración de la wallet Origin! (Irhis).

fix(node): build-spec emite el chain spec REAL cuando el binario lleva el WASM.
- Antes, aunque el binario llevara el WASM real, emitía siempre el de mayo, con :code = «0x»
  simulado, y --raw no sacaba el génesis en crudo.
- Ahora usa el mismo spec con el que arranca run (node_chain_spec), y --raw lleva el génesis
  entero.
- Sin WASM sigue el simulado, pero avisa de que no sirve para unirse a una red. Mainnet sigue
  cerrada por la compuerta L-3.
- Por qué importa, medido hoy: el WASM del runtime NO es reproducible entre máquinas. El mismo
  commit compilado en el Mac y en Linux da génesis distintos (0xe80c… frente a 0x0926…), y el
  nodo del Mac baneó al de la rp1 con «Genesis mismatch». El génesis tiene que fijarlo un chain
  spec que se reparte, no quien compila.
- arrancar.sh usa ~/origin-chain/casa.json cuando existe (exportado en la propia rp1). Así un
  binario nuevo nunca crea otro génesis sobre los mismos datos.

Medido en vivo el 24-oct, todo por RPC firmado como un wallet:
- Nodo en la rp1 (Pi 5, Debian 13): bloques cada 6 s y finalidad a 2-3 bloques. RSS ~200 MB y
  afinidad 0-2 con nice 10.
- El vigilante de cron lo resucita con el mismo peer id
  (12D3KooWDWm5p3Z8Y5DddRki6M6nM1A2xUVQzPqNU1DW53uB6BVi) y sin regenerar la llave.
- E2E en la rp1: remark → ExtrinsicSuccess; finalize_override → ProposalNotFound; uphold0 →
  ZeroWeightWindowVote.
- casa.json exportado en la rp1 = estado del bloque 0 de la cadena viva: 46 de 46 claves
  idénticas. El nodo reinició sobre él con el mismo génesis y siguió desde el #155.
- Red de dos máquinas por la LAN: el nodo del Mac, con casa.json y la rp1 como bootnode,
  sincronizó (mismo best, mismo finalizado). Una transacción enviada al nodo del Mac la incluyó
  la rp1 en el bloque #167, con el mismo hash blake2-256 que devolvió author_submitExtrinsic.

Defectos encontrados en mis propios scripts antes de dejarlos publicados:
- desplegar.sh instalaba un crontab VACÍO: con set -e, el grep -v sobre un crontab vacío
  abortaba la subshell antes de los echo.
- medir.sh dejaba best/finalizado en NA: set -u con $2 sin definir, y stderr se iba con cron.
- max-de-n.py reescribía 16416 como 16_416 (la prueba de identidad lo cazó).

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-24 13:19:52 -05:00