diff --git a/App/lib/core/Handles/HandlesTranslator.vp b/App/lib/core/Handles/HandlesTranslator.vp index f6aee51..fc5e903 100644 --- a/App/lib/core/Handles/HandlesTranslator.vp +++ b/App/lib/core/Handles/HandlesTranslator.vp @@ -352,6 +352,14 @@ class Translator: return 1 llvmlite.add_param(pool, printf_func, i8_ptr_ty, "fmt") printf_func.IsVarArg = 1 + # 诊断(builtins.vp dump 卡死根因排查):printf.fmt Param 创建后立即 + # 校验其 Next——区分"创建即损坏"(create_declare/add_param 环节问题) + # 与"后续被越界写破坏"(dump 时遍历成环)。next=0 为正常。 + dbg_p0: llvmlite.Param | t.CPtr = llvmlite.function_get_param_head(printf_func) + if dbg_p0 is not None: + dbg_p0n: llvmlite.Param | t.CPtr = llvmlite.param_get_next(dbg_p0) + stdio.printf("[DIAG] printf.fmt 创建后: param=%llu next=%llu\n", + t.CUInt64T(dbg_p0), t.CUInt64T(dbg_p0n)) # 声明 LLVM va_start/va_end intrinsic(供 *args 函数体内使用) # declare void @llvm.va_start(i8*) @@ -590,6 +598,26 @@ class Translator: return if _mbuddy is None: return + # 诊断(builtins.vp dump 卡死根因排查,仅 stub 模式打印一次): + # 模块函数清单 + 每个函数首个参数地址/Next 值(步数上限防成环死循环)。 + # 确认 printf declare 的创建上下文与 Params 链损坏状态。 + if mode == llvmlite.OUTPUT_STUB: + dbg_f: llvmlite.Function | t.CPtr = llvmlite.module_get_func_head(self.Module) + dbg_steps: int = 0 + while dbg_f is not None: + dbg_steps += 1 + if dbg_steps > 100000: + stdio.printf("[DIAG] 模块函数链遍历超限(dump_ir 诊断)\n") + stdlib.exit(1) + dbg_name: str = llvmlite.function_get_name(dbg_f) + dbg_p: llvmlite.Param | t.CPtr = llvmlite.function_get_param_head(dbg_f) + if dbg_p is not None: + dbg_pn: llvmlite.Param | t.CPtr = llvmlite.param_get_next(dbg_p) + stdio.printf("[DIAG] 模块函数: %s param0=%llu next=%llu\n", + dbg_name, t.CUInt64T(dbg_p), t.CUInt64T(dbg_pn)) + else: + stdio.printf("[DIAG] 模块函数: %s (无参数)\n", dbg_name) + dbg_f = llvmlite.function_get_next(dbg_f) buf[0] = '\0' llvmlite.LLVMModulePrint(buf, size, self.Module, _mbuddy, mode) diff --git a/App/lib/core/Phase1Main.vp b/App/lib/core/Phase1Main.vp index 23a3cbe..9f96ab1 100644 --- a/App/lib/core/Phase1Main.vp +++ b/App/lib/core/Phase1Main.vp @@ -827,6 +827,19 @@ def RunPhase1(mb: memhub.MemBuddy | t.CPtr, includes_dir: str, temp_dir: str, failed += 1 continue + # 诊断(builtins.vp dump 卡死根因排查):pre_rc 哨兵在 translate 前, + # 覆盖不到 translate 期间的 AST/IR 写穿。dump 前立即检查存活块 + # header/canary(rc=6 块尾 canary 损坏=越界写穿数据区),把"dump + # 时链表成环卡死"变成"定位到 translate 期间写穿发生的文件"。 + post_rc: t.CInt = mb.check_alive_blocks(mark1) + if post_rc != 0: + fb: str = VLogger.fmt_buf() + if fb is not None: + viperlib.snprintf(fb, 1024, + "内存损坏(translate后存活块, rc=%d): %s", post_rc, file_path) + VLogger.error(fb, "Phase1") + stdlib.exit(1) + # dump stub IR(declarations only) PHASE1_IR_SIZE: t.CSizeT = 1048576 stub_buf: bytes = stdlib.malloc(PHASE1_IR_SIZE)