mirror of
https://github.com/pjh456/OxideJS.git
synced 2026-10-23 18:21:13 +08:00
fix: test262 runner 进程 RSS 无界增长——session 收尾统一释放内建裸堆区/upvalue 别名 + 每测试分配上限 256MiB(任务 116)
- 泄漏修复:KernelSession 收尾(teardown_intrinsic_protos/free_session_upvalues) 释放内建对象 Box::into_raw 裸堆区(release_raw_heap 四区置空幂等)与 session upvalue 原件/晋升克隆别名去重释放;bindings 原生盒负载边、 session_gc 边记录、vm_props 属性区同步收尾 - 失控测试封顶:runner kernel max_alloc_bytes=256MiB(dispatch 采样口径 run_alloc_bytes/run_alloc_bytes_full),超限计 memory-limit 失败而非拖垮 进程 RSS(arena 高水位 GB 级 × 多 worker = 宿主 OOM) - 归属:RSS 泄漏 pre-existing(HEAD 无 WIP 同现);identifiers escaped unicode 挂死族另立 B132(pre-existing,supervise 超时自愈) - 验证:build/clippy/四 crate 测试全绿零新增告警;language 前 5000 测试 单窗峰值 330MB(旧 ~4.5MB/测试 单调增长→88GB OOM 签名消失), 窗口间峰值 0.17-1.6GB 有界、逐测试释放回基线
This commit is contained in:
@@ -870,6 +870,7 @@ fn classify_vm_error(e: &str, neg: Option<&Negative>, no_skip: bool) -> TestOutc
|
||||
|| e.contains("not supported")
|
||||
|| e.contains("unsupported")
|
||||
|| e.contains("step limit")
|
||||
|| e.contains("memory limit")
|
||||
|| e.contains("NEW_EXPRESSION")
|
||||
|| e.contains("GET_PROP_DYNAMIC on non-object")
|
||||
|| e.contains("SET_PROP_DYNAMIC on non-object")
|
||||
@@ -1467,6 +1468,11 @@ fn build_runner_kernel() -> Arc<KernelCore> {
|
||||
kernel_config.max_call_depth = 256;
|
||||
kernel_config.min_pool_size = 1;
|
||||
kernel_config.max_pool_size = Some(1);
|
||||
// 单测试分配上限:死循环类测试触步数上限时持续分配,arena 高水位可达 GB
|
||||
// 级;多 worker 并发下进程 RSS 包络被各 worker 当前高水位顶起,全量运行
|
||||
// 必然 OOM。正规测试峰值 ≤132MB(Array 块 p100 实测),256MiB 留有余量
|
||||
// 且把失控测试的驻留面封顶到上限本身。
|
||||
kernel_config.max_alloc_bytes = Some(256 * 1024 * 1024);
|
||||
KernelCore::new(kernel_config)
|
||||
}
|
||||
|
||||
@@ -1509,6 +1515,8 @@ fn categorize_fail(msg: &str) -> (String, String) {
|
||||
("vm: not yet implemented".into(), String::new())
|
||||
} else if reason.contains("step limit") {
|
||||
("vm: step limit".into(), String::new())
|
||||
} else if reason.contains("memory limit") {
|
||||
("vm: memory limit".into(), String::new())
|
||||
} else if reason.contains("not defined") {
|
||||
("vm: not defined".into(), parse_undefined_ident(msg).unwrap_or("").to_string())
|
||||
} else if reason.contains("unsupported") {
|
||||
@@ -1933,6 +1941,14 @@ mod tests {
|
||||
}
|
||||
}
|
||||
|
||||
/// 分配上限超限(与步数上限同款运行期限制):默认 skip,`--no-skip` 下 fail。
|
||||
#[test]
|
||||
fn memory_limit_errors_skip_by_default() {
|
||||
let e = "vm error: VM memory limit 268435456 exceeded (used 268436480) at pc=14";
|
||||
assert_outcome(e, None, false, &TestOutcome::Skip("".into()));
|
||||
assert_outcome(e, None, true, &TestOutcome::Fail("".into()));
|
||||
}
|
||||
|
||||
/// 能力未实现形态保留 skip;`--no-skip` 下转 fail。
|
||||
#[test]
|
||||
fn unimplemented_shapes_stay_skipped() {
|
||||
@@ -2030,6 +2046,10 @@ mod tests {
|
||||
("uncaught ReferenceError: foo is not defined", ("vm: not defined", "foo")),
|
||||
("compile error: Identifier 'x' is not defined", ("compile: not defined", "x")),
|
||||
("vm error: IC_GET_PROP on non-object", ("vm: IC_GET_PROP on non-object", "")),
|
||||
(
|
||||
"vm error: VM memory limit 268435456 exceeded (used 268436480) at pc=14",
|
||||
("vm: memory limit", ""),
|
||||
),
|
||||
("vm error: TypeError: method called on incompatible receiver", ("vm: other", "")),
|
||||
("engine panic: boom", ("engine panic", "")),
|
||||
(
|
||||
|
||||
Reference in New Issue
Block a user