Phase 33 NORM canon test: enforce normalized dev route for P1/P2/JP mini

This commit is contained in:
nyash-codex
2025-12-11 20:54:33 +09:00
parent 59a985b7fa
commit af6f95cd4b
170 changed files with 4423 additions and 1897 deletions

View File

@ -68,16 +68,14 @@ impl MirInterpreter {
})
.unwrap_or(1_000_000);
let mut steps: u64 = 0;
let trace_log_path: Option<String> = std::env::var("NYASH_VM_TRACE_LOG")
.ok()
.map(|v| {
let trimmed = v.trim();
if trimmed.is_empty() || trimmed == "1" {
"__mir__.log".to_string()
} else {
v
}
});
let trace_log_path: Option<String> = std::env::var("NYASH_VM_TRACE_LOG").ok().map(|v| {
let trimmed = v.trim();
if trimmed.is_empty() || trimmed == "1" {
"__mir__.log".to_string()
} else {
v
}
});
loop {
steps += 1;

View File

@ -313,7 +313,10 @@ impl MirInterpreter {
("ConsoleBox", 400) => {
// log/println
if let VMValue::BoxRef(bx) = receiver {
if let Some(console) = bx.as_any().downcast_ref::<crate::boxes::console_box::ConsoleBox>() {
if let Some(console) = bx
.as_any()
.downcast_ref::<crate::boxes::console_box::ConsoleBox>()
{
let message = if args.len() > 1 {
self.reg_load(args[1])?.to_string()
} else if args.len() > 0 {
@ -330,7 +333,10 @@ impl MirInterpreter {
("ConsoleBox", 401) => {
// warn
if let VMValue::BoxRef(bx) = receiver {
if let Some(console) = bx.as_any().downcast_ref::<crate::boxes::console_box::ConsoleBox>() {
if let Some(console) = bx
.as_any()
.downcast_ref::<crate::boxes::console_box::ConsoleBox>()
{
let message = if args.len() > 1 {
self.reg_load(args[1])?.to_string()
} else if args.len() > 0 {
@ -347,7 +353,10 @@ impl MirInterpreter {
("ConsoleBox", 402) => {
// error
if let VMValue::BoxRef(bx) = receiver {
if let Some(console) = bx.as_any().downcast_ref::<crate::boxes::console_box::ConsoleBox>() {
if let Some(console) = bx
.as_any()
.downcast_ref::<crate::boxes::console_box::ConsoleBox>()
{
let message = if args.len() > 1 {
self.reg_load(args[1])?.to_string()
} else if args.len() > 0 {
@ -364,7 +373,10 @@ impl MirInterpreter {
("ConsoleBox", 403) => {
// clear
if let VMValue::BoxRef(bx) = receiver {
if let Some(console) = bx.as_any().downcast_ref::<crate::boxes::console_box::ConsoleBox>() {
if let Some(console) = bx
.as_any()
.downcast_ref::<crate::boxes::console_box::ConsoleBox>()
{
console.clear();
return Ok(VMValue::Void);
}
@ -405,7 +417,10 @@ impl MirInterpreter {
// Plugin Box methods (slot >= 1000)
(_, slot) if slot >= 1000 => {
if let VMValue::BoxRef(bx) = receiver {
if let Some(_p) = bx.as_any().downcast_ref::<crate::runtime::plugin_loader_v2::PluginBoxV2>() {
if let Some(_p) = bx
.as_any()
.downcast_ref::<crate::runtime::plugin_loader_v2::PluginBoxV2>()
{
let host = crate::runtime::plugin_loader_unified::get_global_plugin_host();
let _host = host.read().unwrap();
let _argv = self.load_args_as_boxes(args)?;
@ -447,22 +462,20 @@ impl MirInterpreter {
// 2. Lookup type in TypeRegistry and get slot
// Note: Try exact arity first, then try with args.len()-1 (in case receiver is duplicated in args)
let slot = crate::runtime::type_registry::resolve_slot_by_name(
type_name,
method,
args.len(),
).or_else(|| {
// Fallback: try with one less argument (receiver might be in args)
if args.len() > 0 {
crate::runtime::type_registry::resolve_slot_by_name(
type_name,
method,
args.len() - 1,
)
} else {
None
}
});
let slot =
crate::runtime::type_registry::resolve_slot_by_name(type_name, method, args.len())
.or_else(|| {
// Fallback: try with one less argument (receiver might be in args)
if args.len() > 0 {
crate::runtime::type_registry::resolve_slot_by_name(
type_name,
method,
args.len() - 1,
)
} else {
None
}
});
if let Some(slot) = slot {
// 3. Use unified dispatch
@ -489,9 +502,8 @@ impl MirInterpreter {
if let Some(arg_id) = args.get(0) {
let ch = self.reg_load(*arg_id)?.to_string();
let c = ch.chars().next().unwrap_or('\0');
let is_alpha = ('A'..='Z').contains(&c)
|| ('a'..='z').contains(&c)
|| c == '_';
let is_alpha =
('A'..='Z').contains(&c) || ('a'..='z').contains(&c) || c == '_';
return Ok(VMValue::Bool(is_alpha));
} else {
return Err(self.err_invalid("is_alpha requires 1 argument"));
@ -520,12 +532,7 @@ impl MirInterpreter {
let host = crate::runtime::plugin_loader_unified::get_global_plugin_host();
let host = host.read().unwrap();
let argv = self.load_args_as_boxes(args)?;
match host.invoke_instance_method(
&p.box_type,
method,
p.inner.instance_id,
&argv,
) {
match host.invoke_instance_method(&p.box_type, method, p.inner.instance_id, &argv) {
Ok(Some(ret)) => return Ok(VMValue::from_nyash_box(ret)),
Ok(None) => return Ok(VMValue::Void),
Err(e) => {

View File

@ -253,11 +253,7 @@ impl MirInterpreter {
}
};
if std::env::var("NYASH_EMIT_MIR_TRACE")
.ok()
.as_deref()
== Some("1")
{
if std::env::var("NYASH_EMIT_MIR_TRACE").ok().as_deref() == Some("1") {
if let Some(name) = chosen_name {
eprintln!("[vm/entry] main={}", name);
}

View File

@ -194,9 +194,7 @@ impl StaticBoxRegistry {
/// 登録済み/検出済みの静的Box名一覧
pub fn all_box_names(&self) -> impl Iterator<Item = &String> {
self.declarations
.keys()
.chain(self.detected_boxes.iter())
self.declarations.keys().chain(self.detected_boxes.iter())
}
/// declarations への直接アクセス (既存コードとの互換性)
@ -250,7 +248,7 @@ mod tests {
"JsonParserBox.parse/1".to_string(),
"JsonParserBox.toString/0".to_string(),
"ProgramJSONBox.get/1".to_string(),
"Main.main/0".to_string(), // 除外される
"Main.main/0".to_string(), // 除外される
"StringBox.length/0".to_string(), // 除外される
];