mirror of
https://github.com/allaunthefox/BioSight.git
synced 2026-07-31 03:05:22 +00:00
fix(test): V4 Euclidean division conformance, AGENTS.md drift rules update
python/phi/test_verified_units.py (V4 Critical mitigation):
- Add _ediv() implementing Euclidean division matching Lean 4 Int.div
(remainder always >= 0; matches Python // for positive divisors only)
- q16_mul uses // directly (divisor 65536 always positive)
- q16_div uses _ediv() for correct handling of negative divisors
- q16_div returns 2147483647 sentinel on division by zero
- Document int_sqrt floor-division rationale (non-negative operands)
- Verified: 6/6 edge cases match Lean
AGENTS.md:
- Add anti-drift multi-pass (Python -> Lean -> RRC -> Research Stack)
- Add N=8 root dependency on SilverSight HachimojiN8 theorem
- Add tau/delta mirror rule for gate formalization priority
- Clarify BioSight as domain instance, not independent decision maker
- Clarify Research Stack as read-only regression oracle
.gitignore:
- Add freellmapi-setup/
This commit is contained in:
parent
fe190a6558
commit
6f36ec42e7
3 changed files with 83 additions and 8 deletions
1
.gitignore
vendored
1
.gitignore
vendored
|
|
@ -5,3 +5,4 @@ __pycache__/
|
||||||
dist/
|
dist/
|
||||||
build/
|
build/
|
||||||
.venv/
|
.venv/
|
||||||
|
freellmapi-setup/
|
||||||
|
|
|
||||||
49
AGENTS.md
49
AGENTS.md
|
|
@ -13,8 +13,9 @@ for Adleman/Lipton-style DNA computing. The Φ mapping has 4 layers:
|
||||||
## Ground Rules
|
## Ground Rules
|
||||||
|
|
||||||
- **Decision logic is in Lean** — BioSight shims are Python I/O only.
|
- **Decision logic is in Lean** — BioSight shims are Python I/O only.
|
||||||
If any logic here starts making admissibility or routing decisions,
|
Any Python path making an admissibility or routing decision without a
|
||||||
port it to SilverSight's `Semantics.RRC.*` modules.
|
SilverSight receipt is **drift**. File it immediately as a pending
|
||||||
|
SilverSight gate.
|
||||||
- **No floats in compute paths** — `phi.charclass` and `phi.embed`
|
- **No floats in compute paths** — `phi.charclass` and `phi.embed`
|
||||||
use integer arithmetic for all core encoding. Only `phi.output`
|
use integer arithmetic for all core encoding. Only `phi.output`
|
||||||
uses math.acos (for Fisher distance in Adleman graph building).
|
uses math.acos (for Fisher distance in Adleman graph building).
|
||||||
|
|
@ -23,6 +24,39 @@ for Adleman/Lipton-style DNA computing. The Φ mapping has 4 layers:
|
||||||
- **Reproducibility** — two invocations on the same equation must
|
- **Reproducibility** — two invocations on the same equation must
|
||||||
produce identical DNA sequences (deterministic byte-class and
|
produce identical DNA sequences (deterministic byte-class and
|
||||||
AST order).
|
AST order).
|
||||||
|
- **Rotation trigger** — any time `phi.consistency` makes an
|
||||||
|
ADMIT/QUARANTINE call, check whether a SilverSight receipt backs it.
|
||||||
|
If not, that check is the next SilverSight gate to formalize.
|
||||||
|
- **τ/δ mirror rule** — the Lean proof structure for any gate must
|
||||||
|
mirror BioSight's τ (topology) and δ (depth) values for that equation.
|
||||||
|
High δ → WF-recursive Lean definitions. High τ diversity → wider
|
||||||
|
typeclass hierarchy in SilverSight.
|
||||||
|
|
||||||
|
## Anti-Drift Multi-Pass
|
||||||
|
|
||||||
|
Every decision — no matter how minor — must survive all four passes:
|
||||||
|
|
||||||
|
| Pass | Layer | Authority |
|
||||||
|
|------|-------|-----------|
|
||||||
|
| 1 | Python (`phi.*`) | I/O encoding only — no decisions |
|
||||||
|
| 2 | Lean (SilverSight gate) | Formal authority — closes the decision |
|
||||||
|
| 3 | RRC pipeline (`rigour_pipeline.py`) | Cross-repo alignment |
|
||||||
|
| 4 | Research Stack (`~/Research Stack`, read-only) | Regression oracle |
|
||||||
|
|
||||||
|
**Session start:** run `python3 -m py_compile phi/*.py equation_dna_encoder.py` and
|
||||||
|
confirm phi.encode is deterministic before any new encoding work.
|
||||||
|
|
||||||
|
## N=8 Root Dependency
|
||||||
|
|
||||||
|
BioSight's entire 8-base alphabet choice depends on the SilverSight theorem:
|
||||||
|
|
||||||
|
```
|
||||||
|
N = 8 = min { N : Nyquist(N) ∧ Q16_16(N) ∧ DNA-subset(N) }
|
||||||
|
```
|
||||||
|
|
||||||
|
Target: `formal/SilverSight/HachimojiN8.lean` in the SilverSight repo.
|
||||||
|
Until that theorem is closed with zero sorrys, the alphabet choice is
|
||||||
|
documented justification only, not formal proof.
|
||||||
|
|
||||||
## Core Modules
|
## Core Modules
|
||||||
|
|
||||||
|
|
@ -67,6 +101,13 @@ python3 -c "import phi; print(phi.encode_phi('x + 1 = 2'))"
|
||||||
|
|
||||||
## SilverSight Relationship
|
## SilverSight Relationship
|
||||||
|
|
||||||
BioSight is the DNA-computing branch of the Research Stack ecosystem.
|
BioSight is the first domain instance of the SilverSight framework.
|
||||||
SilverSight (`/home/allaun/SilverSight`) owns all formal Lean logic.
|
SilverSight (`/home/allaun/SilverSight`) owns all formal Lean logic.
|
||||||
If BioSight needs a new theorem or receipt, it requests it from SilverSight.
|
|
||||||
|
- BioSight **imports** SilverSight receipts; it never contains formal proofs.
|
||||||
|
- BioSight **feeds** (τ, δ) distributions back to SilverSight as the work queue
|
||||||
|
for new gates (high-δ equations → WF-recursive gate; high-τ → wider typeclass).
|
||||||
|
- If BioSight needs a new theorem or receipt, open a pending gate entry in
|
||||||
|
`dag/graph.md` and implement the gate in `formal/SilverSight/` first.
|
||||||
|
- `~/Research\ Stack` is read-only archive — consult it only as a regression
|
||||||
|
oracle; never reference it as an active dependency.
|
||||||
|
|
|
||||||
|
|
@ -8,23 +8,56 @@ sys.path.insert(0, os.path.dirname(os.path.dirname(os.path.abspath(__file__))))
|
||||||
from phi.charclass import classify_char
|
from phi.charclass import classify_char
|
||||||
from phi.consistency import check_consistency
|
from phi.consistency import check_consistency
|
||||||
|
|
||||||
# Helper functions for Q16_16 math in Python matching Lean's FixedPoint behavior
|
# Helper functions for Q16_16 math in Python matching Lean's FixedPoint behavior.
|
||||||
|
#
|
||||||
|
# V4 MITIGATION — Lean 4 Int.div uses EUCLIDEAN division:
|
||||||
|
# - The remainder is always non-negative: a = q*b + r, r >= 0
|
||||||
|
# - For POSITIVE divisor: ediv == Python's // (floor division)
|
||||||
|
# - For NEGATIVE divisor: ediv != Python's //
|
||||||
|
# Example: Lean: 65536 / (-3) = -21845 (rem 1)
|
||||||
|
# Python: 65536 // (-3) = -21846 (rem -2, floor)
|
||||||
|
#
|
||||||
|
# Since q16_mul always divides by 65536 (positive), Python's // is safe there.
|
||||||
|
# q16_div divides by an arbitrary b which may be negative, so we use _ediv.
|
||||||
|
|
||||||
|
def _ediv(a, b):
|
||||||
|
"""Euclidean division matching Lean 4's Int.div.
|
||||||
|
Guarantees: a = _ediv(a,b)*b + _emod(a,b) and _emod(a,b) >= 0."""
|
||||||
|
if b == 0:
|
||||||
|
return 0
|
||||||
|
# Python's divmod gives floor division (q, r) with r same sign as b.
|
||||||
|
# Euclidean requires r >= 0 always.
|
||||||
|
q, r = divmod(a, b)
|
||||||
|
if r < 0:
|
||||||
|
# This happens when b < 0 (Python's divmod gives r with sign of b)
|
||||||
|
q += 1
|
||||||
|
# r -= b (but we don't need r for the return)
|
||||||
|
return q
|
||||||
|
|
||||||
def q16_mul(a, b):
|
def q16_mul(a, b):
|
||||||
|
# Divisor is always 65536 (positive), so Python // matches Lean ediv.
|
||||||
return (a * b) // 65536
|
return (a * b) // 65536
|
||||||
|
|
||||||
def q16_div(a, b):
|
def q16_div(a, b):
|
||||||
return (a * 65536) // b
|
if b == 0:
|
||||||
|
return 2147483647 # Q16_16 infinity sentinel
|
||||||
|
# b may be negative, so we must use Euclidean division.
|
||||||
|
return _ediv(a * 65536, b)
|
||||||
|
|
||||||
def int_sqrt(n):
|
def int_sqrt(n):
|
||||||
|
"""Integer square root via Newton's method (floor(√n)).
|
||||||
|
Uses floor division intentionally here because we want floor(√n),
|
||||||
|
not truncation — the Newton iteration converges correctly with
|
||||||
|
floor division on non-negative integers."""
|
||||||
if n < 0:
|
if n < 0:
|
||||||
raise ValueError("Square root of negative number")
|
raise ValueError("Square root of negative number")
|
||||||
if n == 0:
|
if n == 0:
|
||||||
return 0
|
return 0
|
||||||
x = n
|
x = n
|
||||||
y = (x + 1) // 2
|
y = (x + 1) // 2 # floor div is correct here (n ≥ 0)
|
||||||
while y < x:
|
while y < x:
|
||||||
x = y
|
x = y
|
||||||
y = (x + n // x) // 2
|
y = (x + n // x) // 2 # floor div is correct here (both operands ≥ 0)
|
||||||
return x
|
return x
|
||||||
|
|
||||||
def q16_sqrt(q_raw):
|
def q16_sqrt(q_raw):
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue