fix(emit): stabilize Stage-B wrapper with temp file approach

Root Cause:
- Subshell CODE expansion became path literal "/cat/tmp/matmul.hako"
- Variable lost in nested subshell with cd command
- All benchmark cases (matmul, arraymap, etc.) failed emit

Solution:
- Temp file approach with trap cleanup (CODE_TMP=$(mktemp))
- 3-tier fallback extraction (Python→awk→ruby)
- Enhanced diagnostics with HAKO_SELFHOST_TRACE=1
- Pre-check SKIP logic in microbench for unstable emit

Changes:
- tools/hakorune_emit_mir.sh
  - Temp file approach eliminates subshell variable issues
  - extract_program_json now has 3 fallback strategies
  - Detailed trace output for debugging
  - Variable scope fixes (local → script level)
- tools/perf/microbench.sh
  - matmul pre-check with SKIP + diagnostic hint
  - Prevents false benchmark results on emit failure

Test Results:
 loop:        936 bytes   rc=0
 call:        330 bytes   rc=0
 stringchain: 313 bytes   rc=0
 arraymap:    422 bytes   rc=0
 matmul:     7731 bytes   rc=0 (FIXED!)
 CI guard: emit_provider_no_jsonfrag_canary PASS

Impact:
- All benchmark cases now emit MIR successfully
- Stable execution without subshell variable bugs
- Comprehensive diagnostics for future debugging
- Foundation for provider-first optimization

Next: Apply AotPrep to optimize Array/Map hot paths

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
nyash-codex
2025-11-13 22:52:25 +09:00
parent 8b44c5009f
commit 647ee05d06
3 changed files with 245 additions and 24 deletions

View File

@ -22,15 +22,23 @@ static box Main {
main(args) {
// 1) Collect source from args or env
local src = null
local src_file = null
if args != null {
local i = 0
local n = args.length()
loop(i < n) {
local t = "" + args.get(i)
if t == "--source" && i + 1 < n { src = "" + args.get(i + 1) break }
if t == "--source-file" && i + 1 < n { src_file = "" + args.get(i + 1) i = i + 1 }
i = i + 1
}
}
// Prefer explicit source string when provided
// If --source-file is used, prefer env-provided content (wrapper supplies HAKO_SOURCE_FILE_CONTENT)
if src == null && src_file != null {
local inline = env.get("HAKO_SOURCE_FILE_CONTENT")
if inline != null { src = "" + inline }
}
// Skip env.local.get check - Stage-3 keyword conflict
// Original: if src == null { src = env.local.get("HAKO_SOURCE") }
if src == null { src = "return 0" }