Files
hakorune/apps/selfhost/vm/boxes/mir_vm_m2.nyash
nyash-codex 510f4cf523 builder/vm: stabilize json_lint_vm under unified calls
- Fix condition_fn resolution: Value call path + dev safety + stub injection
- VM bridge: handle Method::birth via BoxCall; ArrayBox push/get/length/set direct bridge
- Receiver safety: pin receiver in method_call_handlers to avoid undefined use across blocks
- Local vars: materialize on declaration (use init ValueId; void for uninit)
- Prefer legacy BoxCall for Array/Map/String/user boxes in emit_box_or_plugin_call (stability-first)
- Test runner: update LLVM hint to llvmlite harness (remove LLVM_SYS_180_PREFIX guidance)
- Docs/roadmap: update CURRENT_TASK with unified default-ON + guards

Note: NYASH_DEV_BIRTH_INJECT_BUILTINS=1 can re-enable builtin birth() injection during migration.
2025-09-28 12:19:49 +09:00

113 lines
3.9 KiB
Plaintext
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

// mir_vm_m2.nyash — Ny製の最小MIR(JSON v0)実行器M2: const/binop/ret
static box MirVmM2 {
_str_to_int(s) {
local i = 0
local n = s.length()
local acc = 0
loop (i < n) {
local ch = s.substring(i, i+1)
if ch == "0" { acc = acc * 10 + 0 i = i + 1 continue }
if ch == "1" { acc = acc * 10 + 1 i = i + 1 continue }
if ch == "2" { acc = acc * 10 + 2 i = i + 1 continue }
if ch == "3" { acc = acc * 10 + 3 i = i + 1 continue }
if ch == "4" { acc = acc * 10 + 4 i = i + 1 continue }
if ch == "5" { acc = acc * 10 + 5 i = i + 1 continue }
if ch == "6" { acc = acc * 10 + 6 i = i + 1 continue }
if ch == "7" { acc = acc * 10 + 7 i = i + 1 continue }
if ch == "8" { acc = acc * 10 + 8 i = i + 1 continue }
if ch == "9" { acc = acc * 10 + 9 i = i + 1 continue }
break
}
return acc
}
_int_to_str(n) {
if n == 0 { return "0" }
local v = n
local out = ""
loop (v > 0) {
local d = v % 10
local ch = "0"
if d == 1 { ch = "1" } else { if d == 2 { ch = "2" } else { if d == 3 { ch = "3" } else { if d == 4 { ch = "4" } else { if d == 5 { ch = "5" } else { if d == 6 { ch = "6" } else { if d == 7 { ch = "7" } else { if d == 8 { ch = "8" } else { if d == 9 { ch = "9" } } } } } } } }
out = ch + out
v = v / 10
}
return out
}
_find_int_in(seg, keypat) {
local p = seg.indexOf(keypat)
if p < 0 { return null }
p = p + keypat.length()
local i = p
local out = ""
loop(true) {
local ch = seg.substring(i, i+1)
if ch == "" { break }
if ch == "0" || ch == "1" || ch == "2" || ch == "3" || ch == "4" || ch == "5" || ch == "6" || ch == "7" || ch == "8" || ch == "9" { out = out + ch i = i + 1 } else { break }
}
if out == "" { return null }
return me._str_to_int(out)
}
_find_str_in(seg, keypat) {
local p = seg.indexOf(keypat)
if p < 0 { return "" }
p = p + keypat.length()
local q = seg.indexOf(""", p)
if q < 0 { return "" }
return seg.substring(p, q)
}
_get(regs, id) { if regs.has(id) { return regs.get(id) } return 0 }
_set(regs, id, v) { regs.set(id, v) }
_bin(kind, a, b) {
if kind == "Add" { return a + b }
if kind == "Sub" { return a - b }
if kind == "Mul" { return a * b }
if kind == "Div" { if b == 0 { return 0 } else { return a / b } }
return 0
}
run(json) {
local regs = new MapBox()
local pos = json.indexOf(""instructions":[")
if pos < 0 {
print("0")
return 0
}
local cur = pos
loop(true) {
local op_pos = json.indexOf(""op":"", cur)
if op_pos < 0 { break }
local name_start = op_pos + 6
local name_end = json.indexOf(""", name_start)
if name_end < 0 { break }
local opname = json.substring(name_start, name_end)
local next_pos = json.indexOf(""op":"", name_end)
if next_pos < 0 { next_pos = json.length() }
local seg = json.substring(op_pos, next_pos)
if opname == "const" {
local dst = me._find_int_in(seg, ""dst":")
local val = me._find_int_in(seg, ""value":{"type":"i64","value":")
if dst != null and val != null { me._set(regs, "" + dst, val) }
} else { if opname == "binop" {
local dst = me._find_int_in(seg, ""dst":")
local kind = me._find_str_in(seg, ""op_kind":"")
local lhs = me._find_int_in(seg, ""lhs":")
local rhs = me._find_int_in(seg, ""rhs":")
if dst != null and lhs != null and rhs != null {
local a = me._get(regs, "" + lhs)
local b = me._get(regs, "" + rhs)
me._set(regs, "" + dst, me._bin(kind, a, b))
}
} else { if opname == "ret" {
local v = me._find_int_in(seg, ""value":")
if v == null { v = 0 }
local out = me._get(regs, "" + v)
print(me._int_to_str(out))
return 0
} } }
cur = next_pos
}
print("0")
return 0
}
}