Files
fhe/scripts/regen-kats.sh
T
Hanzo AI 02fd28b349 fhe: KAT oracle + regen-kats.sh for cross-runtime byte-equality (LP-167)
Lands the Lux FHE-KAT corpus generators consumed by the C++ production
runtime at github.com/luxfi/luxcpp/crypto/fhe (LP-167). Mirrors the
pulsar/lens/warp regen script shape; emits a sha256 manifest and
supports --verify mode for determinism diffing.

Delivered:
  cmd/kat_oracle/main.go               KAT oracle. --emit --out <dir>
                                       writes one JSON entry per
                                       (param_set, seed) tuple. Each
                                       entry pins parameter-set ID,
                                       seed, operation tag, and a
                                       CRC32 fingerprint of the SHA-256
                                       digest of the canonical SecretKey
                                       MarshalBinary output.
  scripts/regen-kats.sh                Driver: runs kat_oracle, runs the
                                       in-tree determinism tests
                                       (TestNewKeyGeneratorFromSeed_Deterministic
                                       + TestNewKeyGeneratorFromSeed_DifferentSeeds),
                                       emits manifest. --verify mode
                                       diffs against existing manifest;
                                       fails on mismatch.
  scripts/regen-kats.manifest.sha256   Initial 4-entry manifest:
                                       PN10QP27 / PN11QP54 × seed-zero /
                                       seed-lp167-stable.

Verification:
  $ LUXCPP_DIR=$HOME/work/luxcpp scripts/regen-kats.sh --verify
  OK: Lux FHE KAT regeneration is byte-equal across runs (4 files)

  $ cd \$HOME/work/luxcpp/crypto/fhe
  $ ctest --test-dir build -R fhe_kat_replay
  OK lux-fhe-cpp KAT replay (4 entries)

LP-167 §"Cross-runtime KAT contract" requires both directions of
byte-equality. The Go→C++ direction is exercised by this commit and
the C++ replay test. The reverse direction (C++ generates, Go
verifies) is queued behind v0.1.0-rc2-fhe-gpu in lockstep with the
production CUDA NTT + key-switch + bootstrap kernels.

go test -count=1 -timeout=300s ./...  ->  3/3 ok
  ok  github.com/luxfi/fhe                 48.345s
  ok  github.com/luxfi/fhe/pkg/encrypted   98.833s
  ok  github.com/luxfi/fhe/pkg/threshold    0.778s
2026-03-03 12:00:00 -08:00

73 lines
2.4 KiB
Bash
Executable File

#!/usr/bin/env bash
# regen-kats.sh — deterministic regeneration + verification of every
# Lux FHE-KAT consumed by the C++ production runtime
# (luxcpp/crypto/fhe/test/cpp/fhe_kat_replay_test).
#
# LP-167 §"Cross-runtime KAT contract" is the binding spec; this
# script enforces the byte-equality invariant.
#
# Default output:
# <luxcpp>/crypto/fhe/test/kat/sk_pn10qp27_seed_zero.json
# <luxcpp>/crypto/fhe/test/kat/sk_pn10qp27_seed_lp167.json
# <luxcpp>/crypto/fhe/test/kat/sk_pn11qp54_seed_zero.json
# <luxcpp>/crypto/fhe/test/kat/sk_pn11qp54_seed_lp167.json
#
# Manifest:
# <fhe>/scripts/regen-kats.manifest.sha256
#
# Modes:
# regen-kats.sh — regenerate corpus + write manifest
# regen-kats.sh --verify — regenerate corpus, diff against
# existing manifest, fail on mismatch
set -euo pipefail
FHE_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
LUXCPP_DIR="${LUXCPP_DIR:-${HOME}/work/luxcpp}"
KAT_BASE="${LUXCPP_DIR}/crypto/fhe"
KAT_OUT="${KAT_BASE}/test/kat"
MANIFEST="${FHE_DIR}/scripts/regen-kats.manifest.sha256"
VERIFY=0
if [[ "${1:-}" == "--verify" ]]; then
VERIFY=1
fi
cd "${FHE_DIR}"
mkdir -p "${KAT_OUT}"
echo "[1/2] kat_oracle --emit --out ${KAT_OUT}"
go run ./cmd/kat_oracle --emit --out "${KAT_OUT}" >/dev/null
echo "[2/2] in-tree determinism test"
go test -count=1 -run "TestNewKeyGeneratorFromSeed_Deterministic|TestNewKeyGeneratorFromSeed_DifferentSeeds" . >/dev/null
# Build sha256 manifest deterministically (sorted by file name).
TMP_MANIFEST="$(mktemp)"
trap 'rm -f "${TMP_MANIFEST}"' EXIT
# Stable order regardless of glob expansion. Paths in the manifest are
# relative to KAT_BASE so the manifest is portable across hosts (different
# ${HOME}).
find "${KAT_OUT}" -maxdepth 1 -name "*.json" -type f | sort | while read -r f; do
rel="${f#${KAT_BASE}/}"
shasum -a 256 "$f" | awk -v p="${rel}" '{print $1" "p}'
done > "${TMP_MANIFEST}"
if [[ "${VERIFY}" == "1" ]]; then
if [[ ! -f "${MANIFEST}" ]]; then
echo "ERROR: --verify requested but no prior manifest at ${MANIFEST}"
exit 2
fi
if ! diff -u "${MANIFEST}" "${TMP_MANIFEST}"; then
echo "FAIL: manifest mismatch — Lux FHE KAT regeneration is non-deterministic" >&2
exit 3
fi
echo "OK: Lux FHE KAT regeneration is byte-equal across runs ($(wc -l < "${MANIFEST}") files)"
else
cp "${TMP_MANIFEST}" "${MANIFEST}"
echo "wrote manifest: ${MANIFEST}"
cat "${MANIFEST}"
fi