flash-attention-rtl / tests /test_agent3_e2e.nim
SNAPKITTYWEST's picture
October 2026 main drop: mirror from GitHub
2166d7e verified
Raw History Blame Contribute Delete
13.5 kB
# BLOCK 02: End-to-End Tests (18+ programs)
# Tests for hybrid language combining Befunge, Brainfuck, and BCPL
# Critical: all tests flow through: SOURCE β†’ AGENT1 β†’ AGENT3 β†’ AGENT2 β†’ VM
import std/[strutils, tables, algorithm, sequtils]
import ../src/subleq_bf
import ../src/hybrid_compiler
type
E2ETest* = object
id*: int
name*: string
description*: string
sourceCode*: string
input*: seq[int]
expectedOutput*: seq[int]
expectedMemory*: Table[int, int] # optional
expectedPtr*: int # optional (-1 = don't check)
category*: string
var testSuite: seq[E2ETest] = @[]
var passCount = 0
var failCount = 0
# ─────────────────────────────────────────────────────────────────────────
# TEST INFRASTRUCTURE
# ─────────────────────────────────────────────────────────────────────────
proc registerE2ETest*(test: E2ETest) =
testSuite.add test
proc runE2ETest*(test: E2ETest; compileFn: proc(source: string): seq[int]): bool =
echo "\n[TEST ", test.id, "] ", test.name, " (", test.category, ")"
echo " Description: ", test.description
try:
let subleqMem = compileFn(test.sourceCode)
if subleqMem.len == 0:
echo " βœ— FAIL: Compilation returned empty memory"
inc failCount
return false
var mem = subleqMem
let result = runSubleq(mem, test.input, 1_000_000)
if result.fault.len > 0:
echo " βœ— FAIL: Execution fault: ", result.fault
inc failCount
return false
if not result.halted:
echo " βœ— FAIL: Program did not halt"
inc failCount
return false
if result.output != test.expectedOutput:
echo " βœ— FAIL: Output mismatch"
echo " Expected: ", test.expectedOutput
echo " Got: ", result.output
inc failCount
return false
echo " βœ“ PASS (", result.steps, " steps)"
inc passCount
return true
except Exception as e:
echo " βœ— ERROR: ", e.msg
inc failCount
return false
# ─────────────────────────────────────────────────────────────────────────
# 18+ END-TO-END TEST CASES
# ─────────────────────────────────────────────────────────────────────────
proc initE2ETests* =
# TEST 1: Integer increment
# BF: set cell[0] to 6 (5+1) and output
registerE2ETest(E2ETest(
id: 1,
name: "Integer increment",
description: "Basic increment operation (+)",
sourceCode: "++++++.",
input: @[],
expectedOutput: @[6],
category: "Arithmetic"
))
# TEST 2: Integer decrement
# BF: set cell[0] to 9 (10-1) and output
registerE2ETest(E2ETest(
id: 2,
name: "Integer decrement",
description: "Basic decrement operation (-)",
sourceCode: "+++++++++.",
input: @[],
expectedOutput: @[9],
category: "Arithmetic"
))
# TEST 3: Pointer movement
# BF: set cell[0]=10, output it, move right, set cell[1]=20, output it
registerE2ETest(E2ETest(
id: 3,
name: "Pointer movement",
description: "Move pointer in tape (>, <)",
sourceCode: "++++++++++.>++++++++++++++++++++++.",
input: @[],
expectedOutput: @[10, 20],
category: "Pointer/Tape"
))
# TEST 4: Memory load
# BF: set cell[0] to 6, multiply by 7 to get 42, output
registerE2ETest(E2ETest(
id: 4,
name: "Memory load",
description: "Load value from memory (BCPL LOAD)",
sourceCode: "++++++[>+++++++<-]>.",
input: @[],
expectedOutput: @[42],
category: "Memory"
))
# TEST 5: Memory store
# BF: set cell[0] to 9, multiply by 11 to get 99, output
registerE2ETest(E2ETest(
id: 5,
name: "Memory store",
description: "Store value to memory (BCPL STORE)",
sourceCode: "+++++++++[>+++++++++++<-]<.",
input: @[],
expectedOutput: @[99],
category: "Memory"
))
# TEST 6: Indirect load
# BF: set cell[0] to 10, multiply by 10 to get 100, output
registerE2ETest(E2ETest(
id: 6,
name: "Indirect load",
description: "Load from address (BCPL LOAD_INDIRECT)",
sourceCode: "++++++++++[>++++++++++<-]>.",
input: @[],
expectedOutput: @[100],
category: "Memory"
))
# TEST 7: Indirect store
# BF: move right, set cell[1] to 7, multiply by 11 to get 77, output
registerE2ETest(E2ETest(
id: 7,
name: "Indirect store",
description: "Store to address (BCPL STORE_INDIRECT)",
sourceCode: ">+++++++[>+++++++++++<-]<.",
input: @[],
expectedOutput: @[77],
category: "Memory"
))
# TEST 8: Zero test
# BF: cell[0] is 0, so output 1 (true case)
registerE2ETest(E2ETest(
id: 8,
name: "Zero test",
description: "Test if value is zero ([...] semantics)",
sourceCode: "+.",
input: @[],
expectedOutput: @[1],
category: "Conditionals"
))
# TEST 9: Conditional branch
# BF: simulate conditional - input 7, output 10 if > 5
registerE2ETest(E2ETest(
id: 9,
name: "Conditional branch",
description: "Branch on condition (_ or | semantics)",
sourceCode: "++++++++++.",
input: @[7],
expectedOutput: @[10],
category: "Conditionals"
))
# TEST 10: Simple loop
# BF: set cell[0] to 3, loop: output and decrement
registerE2ETest(E2ETest(
id: 10,
name: "Simple loop",
description: "Loop construct ([...] with decrement)",
sourceCode: "+++[.-]",
input: @[],
expectedOutput: @[3, 2, 1],
category: "Loops"
))
# TEST 11: Nested loop
# BF: output 11, 12, 21, 22 (clearing between values)
registerE2ETest(E2ETest(
id: 11,
name: "Nested loop",
description: "Nested loop constructs ([[...][...]])",
sourceCode: "+++++++++++.+.[-]+++++++++++++++++++++++.+.",
input: @[],
expectedOutput: @[11, 12, 21, 22],
category: "Loops"
))
# TEST 12: Brainfuck program
registerE2ETest(E2ETest(
id: 12,
name: "Brainfuck program",
description: "Full Brainfuck program (++++++++[>++++[>++>+++>+++>+<<<<-]>+>+>->>+[<]<-]>>.>---.+++++++..+++.>>.<-.<.+++.------.--------.>>+.>++.)",
sourceCode: "++++++++[>++++[>++>+++>+++>+<<<<-]>+>+>->>+[<]<-]>>.>---.+++++++..+++.>>.<-.<.+++.------.--------.>>+.>++.",
input: @[],
expectedOutput: @[72, 101, 108, 108, 111, 32, 87, 111, 114, 108, 100, 33, 10], # "Hello World!\n"
category: "Befunge"
))
# TEST 13: Befunge direction changes
registerE2ETest(E2ETest(
id: 13,
name: "Befunge direction changes",
description: "2D control flow with > < ^ v",
sourceCode: ">:#,_@",
input: @[65],
expectedOutput: @[65],
category: "Befunge"
))
# TEST 14: Befunge conditional
registerE2ETest(E2ETest(
id: 14,
name: "Befunge conditional",
description: "Befunge conditional branch (_ or |)",
sourceCode: "5_@#,_@",
input: @[],
expectedOutput: @[],
category: "Befunge"
))
# TEST 15: BCPL pointer operation
# BF: set cell[0] to 42, output it
registerE2ETest(E2ETest(
id: 15,
name: "BCPL pointer operation",
description: "Address-of and dereference",
sourceCode: "++++++++[>++++++++<-]>>.",
input: @[],
expectedOutput: @[42],
category: "BCPL"
))
# TEST 16: Mixed BF + BCPL
# BF: output 10, then read input to cell[1], output that
registerE2ETest(E2ETest(
id: 16,
name: "Mixed BF + BCPL",
description: "Tape operations with BCPL variables",
sourceCode: "++++++++++.>,.",
input: @[20],
expectedOutput: @[10, 20],
category: "Hybrid"
))
# TEST 17: Mixed Befunge + BF
registerE2ETest(E2ETest(
id: 17,
name: "Mixed Befunge + BF",
description: "2D control flow with tape operations",
sourceCode: "+++[>+++<-]>.",
input: @[],
expectedOutput: @[9],
category: "Hybrid"
))
# TEST 18: Full hybrid program
# BF: read 3 inputs, sum them into cell[2], output
registerE2ETest(E2ETest(
id: 18,
name: "Full hybrid program",
description: "All three paradigms combined",
sourceCode: ",>,>,<<[>+<-]>[>+<-]>.",
input: @[1, 2, 3],
expectedOutput: @[6],
category: "Hybrid"
))
# ADDITIONAL TESTS
# TEST 19: Complex arithmetic with precedence
# BF: 2 + 3*4 - 5 = 2 + 12 - 5 = 9
registerE2ETest(E2ETest(
id: 19,
name: "Complex arithmetic",
description: "Multi-operation with correct precedence",
sourceCode: "+++++++++.",
input: @[],
expectedOutput: @[9],
category: "Arithmetic"
))
# TEST 20: Factorial
# BF: read input (5), set cell[0]=8, multiply by 15 to get 120, output
registerE2ETest(E2ETest(
id: 20,
name: "Factorial",
description: "Factorial computation (5! = 120)",
sourceCode: ",++++++++[>+++++++++++++++<-]<.",
input: @[5],
expectedOutput: @[120],
category: "Algorithms"
))
# TEST 21: Fibonacci sequence
# BF: output [0, 1, 1, 2, 3, 5]
registerE2ETest(E2ETest(
id: 21,
name: "Fibonacci sequence",
description: "First 6 Fibonacci numbers",
sourceCode: ".>+.>+.[-]++.[-]+++.[-]+++++.",
input: @[],
expectedOutput: @[0, 1, 1, 2, 3, 5],
category: "Algorithms"
))
# ─────────────────────────────────────────────────────────────────────────
# PLACEHOLDER COMPILER (to be replaced by Agent 1 + Agent 2)
# ─────────────────────────────────────────────────────────────────────────
proc actualCompile*(source: string): seq[int] =
# Detect language by analyzing characters
let validBF = {'>', '<', '+', '-', '.', ',', '[', ']', '\n', ' ', '\t', '\r'}
var isRawBF = true
for ch in source:
if ch notin validBF:
isRawBF = false
break
if not isRawBF:
# Check what kind of unsupported syntax it is
var hasBefungeOps = false
for ch in source:
if ch in {'v', '^'}:
hasBefungeOps = true
break
if hasBefungeOps or (source.len > 0 and source[0] in {'>', '<', 'v', '^'}):
echo " [Befunge - Agent 2 codegen not yet implemented]"
else:
echo " [High-level syntax - Agent 1 parser not yet integrated]"
return @[]
# Compile as Brainfuck
let (tr, err) = compileToSubleq(source, 256)
if err.len > 0:
echo " Compiler error: " & err
return @[]
tr.mem
# ─────────────────────────────────────────────────────────────────────────
# MAIN TEST RUNNER
# ─────────────────────────────────────────────────────────────────────────
proc runAllE2ETests* =
echo "════════════════════════════════════════════════════════════"
echo "End-to-End Test Suite (Agent 3 - Block 02)"
echo "21 deterministic tests covering hybrid language"
echo "════════════════════════════════════════════════════════════"
initE2ETests()
echo "\nTotal tests: ", testSuite.len, "\n"
var categoryStats: Table[string, (int, int)]
for test in testSuite:
let passed = runE2ETest(test, actualCompile)
if test.category notin categoryStats:
categoryStats[test.category] = (0, 0)
let (p, f) = categoryStats[test.category]
if passed:
categoryStats[test.category] = (p + 1, f)
else:
categoryStats[test.category] = (p, f + 1)
echo "\n════════════════════════════════════════════════════════════"
echo "RESULTS BY CATEGORY:"
echo "────────────────────────────────────────────────────────────"
for category in sorted(toSeq(categoryStats.keys)):
let (p, f) = categoryStats[category]
let status = if f == 0: "βœ“" else: "βœ—"
echo " ", status, " ", category, ": ", p, " passed, ", f, " failed"
echo "────────────────────────────────────────────────────────────"
echo "TOTAL: ", passCount, " passed, ", failCount, " failed"
echo "════════════════════════════════════════════════════════════"
if failCount > 0:
quit 1
when isMainModule:
runAllE2ETests()