From a8c668002b04a287a831e94dc5bd402c597452f3 Mon Sep 17 00:00:00 2001 From: pjh456 <147148383@qq.com> Date: Fri, 11 Sep 2026 21:19:08 +0000 Subject: [PATCH] =?UTF-8?q?perf:=20test262=20runner=20=E9=87=8D=E5=BB=BA?= =?UTF-8?q?=E4=B8=8E=20sweep=20=E5=8F=8C=E9=92=9F=E4=BA=92=E6=96=A5?= =?UTF-8?q?=E2=80=94=E2=80=94=E9=87=8D=E5=BB=BA=E8=BF=AD=E4=BB=A3=E4=B8=8D?= =?UTF-8?q?=E5=86=8D=E5=AF=B9=20doomed=20=E6=A0=B8=E7=99=BD=E5=81=9A=2050k?= =?UTF-8?q?=20=E6=B8=85=E7=90=86=EF=BC=8Csweep=20=E6=96=87=E6=A1=A3?= =?UTF-8?q?=E5=AF=B9=E9=BD=90=E4=B8=A4=E8=BE=B9=E7=95=8C=E5=A5=91=E7=BA=A6?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- crates/oxide_kernel/src/kernel.rs | 23 ++++++++++++++++------- crates/oxide_test262/src/main.rs | 7 ++++--- 2 files changed, 20 insertions(+), 10 deletions(-) diff --git a/crates/oxide_kernel/src/kernel.rs b/crates/oxide_kernel/src/kernel.rs index 31de5196..386e25cb 100644 --- a/crates/oxide_kernel/src/kernel.rs +++ b/crates/oxide_kernel/src/kernel.rs @@ -209,15 +209,24 @@ impl KernelCore { self.config.max_cached_modules = cap; } - /// 在每次 runner(test262 等)边界清理瞬时 shape/prop 缓存,防止跨测试累积膨胀。 + /// 批边界清理瞬时 shape/prop 缓存,防止跨测试累积膨胀。 /// - /// 字符串 intern 表是 append-only,无需清理;仅当 shape 或 prop 表超过阈值时才执行 - /// [`ShapeForge::clear_transient`] 与 [`PropForge::clear`]。 + /// 瞬时 forge(非根 shape/transition/position + prop 模板)的 id 空间只在两类 + /// 边界复位:(1)kernel 整体重建——新核构造即空(结构性必清;宿主义务 = + /// 重建前旧核无存活 VM,否则旧核连同其 forge 永久驻留);(2)批内兜底 sweep + /// ——本函数,数据依赖:仅当 shape 或 prop 表超过 50k 阈值时才执行 + /// [`ShapeForge::clear_transient`] 与 [`PropForge::clear`](阈值是增长闸门, + /// 宿主的检查节奏只是采样点)。字符串 intern 表 append-only、CodeForge LRU + /// 自管理,均不碰。 + /// + /// # 边界与前提 + /// - 调用点须无存活 VM:对象头与 IC 词持 shape id,清空使 id 空间复位,跨复位 + /// 存活的 VM 会因 id 复用碰撞静默错槽;引擎不自动重建也不自动守卫,该前提 + /// 由宿主契约承担(runner 由循环结构满足:VM 每测试新建即弃,sweep 点在 + /// VM 作用域外)。 pub fn sweep_runner_forges(&self) { - // 键 interner 是 append-only(无逐次清理);只有瞬时 shape/prop 表 - // 需要在 test262 每测试边界做上限约束。 - // test262 每测试新建 VM/session。在该边界,此前测试产生的 JS 对象 - // 不应保留任何瞬时 shape/模板。 + // 键 interner 是 append-only(无逐次清理);仅当瞬时 shape/prop 表超阈值 + // 时清表(批内兜底),调用点无存活 VM 的前提见文档。 if self.shape_forge.len() > 50_000 { self.shape_forge.clear_transient(); self.prop_forge.clear(); diff --git a/crates/oxide_test262/src/main.rs b/crates/oxide_test262/src/main.rs index d878480c..8488f67b 100644 --- a/crates/oxide_test262/src/main.rs +++ b/crates/oxide_test262/src/main.rs @@ -1799,12 +1799,13 @@ fn run_tests() -> bool { tests_since_kernel_reset += 1; let done = progress.fetch_add(1, Ordering::Relaxed) + 1; - if done % 500 == 0 { - kernel.sweep_runner_forges(); - } if tests_since_kernel_reset >= kernel_batch { + // 重建即全新 forge(结构性必清):旧核连同其表整体丢弃, + // 先 sweep 是对 doomed 核白做一次 O(50k) 清理。 kernel = build_runner_kernel(); tests_since_kernel_reset = 0; + } else if done % 500 == 0 { + kernel.sweep_runner_forges(); // 批内 50k 兜底(数据依赖) } if done % 500 == 0 || done == total { test262_info!("progress: {}/{} ({}%)", done, total, done * 100 / total);