refactor(tpv): 形参类型注解解析失败改 fail-fast(不再静默用 i32)
- FuncGenDef 前向声明形参 / 定义签名形参:resolved is None 即 fatal - FuncGenBase create_function 形参:同上(暴露调用方未传 trans 上下文) - ClassGenVTable _translate_method 形参:同上(签名/调用点/实现体三方一致) - TypeGenCDef 整数 CDefine 值缓冲分配失败改 fatal(对齐同文件浮点/字符串分支) - FuncGenMixin._type_byte_size 类型缺失改 fatal(case _ 保留 8,注释说明无布局查询能力)
This commit is contained in:
1 parent
22c71388d4
commit
cc3359faea
5 files changed
+72
-39
No files matched your search
@@ -754,18 +754,24 @@ class ClassGenVTable(ClassGenBase.ClassGenBase):
|
||||
if arg.annotation is not None:
|
||||
resolved: llvmlite.LLVMType | t.CPtr = self.Gen.TypeGenResolve.resolve_annotation_type(
|
||||
pool, arg.annotation, imported_modules, from_imports, trans, 0)
|
||||
if resolved is not None:
|
||||
# 裸类形参 → Ptr(struct):按"对象即指针"引用传参。
|
||||
# 若按 struct 值传参,self.Head = node 会取局部拷贝地址
|
||||
# (append 返回后悬垂,G5 Test4 head.Value 读到垃圾)。
|
||||
# CArray 形参 → 元素指针 ty*(数组衰减,C 语义,与函数形参一致)。
|
||||
match resolved:
|
||||
case llvmlite.LLVMType.Struct(_, _, _):
|
||||
param_ty = llvmlite.Ptr(pool, resolved)
|
||||
case llvmlite.LLVMType.Array(aelem_ty, _):
|
||||
param_ty = llvmlite.Ptr(pool, aelem_ty)
|
||||
case _:
|
||||
param_ty = resolved
|
||||
if resolved is None:
|
||||
# [S4 fail-fast] 有注解但解析失败:不再静默用 i32
|
||||
# (方法签名与调用点/实现体三方不一致)
|
||||
self.Gen.TypeGenErr.fatal_error(
|
||||
arg, f"方法 '{class_name}.{method_name}' 形参 '{arg.arg}' 类型注解解析失败",
|
||||
"NameError")
|
||||
return 0
|
||||
# 裸类形参 → Ptr(struct):按"对象即指针"引用传参。
|
||||
# 若按 struct 值传参,self.Head = node 会取局部拷贝地址
|
||||
# (append 返回后悬垂,G5 Test4 head.Value 读到垃圾)。
|
||||
# CArray 形参 → 元素指针 ty*(数组衰减,C 语义,与函数形参一致)。
|
||||
match resolved:
|
||||
case llvmlite.LLVMType.Struct(_, _, _):
|
||||
param_ty = llvmlite.Ptr(pool, resolved)
|
||||
case llvmlite.LLVMType.Array(aelem_ty, _):
|
||||
param_ty = llvmlite.Ptr(pool, aelem_ty)
|
||||
case _:
|
||||
param_ty = resolved
|
||||
pname: str = pool.alloc(32)
|
||||
if pname is not None:
|
||||
viperlib.snprintf(pname, 32, "%%%s", arg.arg)
|
||||
|
||||
@@ -453,8 +453,14 @@ class FuncGenBase(CallGenBase.CallGenBase):
|
||||
if arg.annotation is not None:
|
||||
resolved: llvmlite.LLVMType | t.CPtr = self.Gen.TypeGenResolve.resolve_annotation_type(
|
||||
pool, arg.annotation, None, None, None, 0)
|
||||
if resolved is not None:
|
||||
param_ty = resolved
|
||||
if resolved is None:
|
||||
# [S4 fail-fast] 有注解但解析失败:不再静默用 i32。
|
||||
# 本函数不传 trans/imports 上下文,解析失败即调用方
|
||||
# 未补齐上下文(暴露上游,不由本函数兜底)。
|
||||
self.Gen.TypeGenErr.fatal_error(
|
||||
arg, f"函数 '{name}' 形参 '{arg.arg}' 类型注解解析失败", "NameError")
|
||||
return None
|
||||
param_ty = resolved
|
||||
pname: str = pool.alloc(32)
|
||||
if pname is not None:
|
||||
viperlib.snprintf(pname, 32, "%%%s", arg.arg)
|
||||
|
||||
@@ -259,16 +259,21 @@ class FuncGenDef(CallGenBase.CallGenBase):
|
||||
if arg.annotation is not None:
|
||||
resolved: llvmlite.LLVMType | t.CPtr = self.Gen.TypeGenResolve.resolve_annotation_type(
|
||||
pool, arg.annotation, imported_modules, from_imports, trans, 0)
|
||||
if resolved is not None:
|
||||
# 裸类形参 → Ptr(struct)(对象即指针,与方法形参一致)
|
||||
# CArray 形参 → 元素指针 ty*(C 数组衰减,与 add_param 一致)
|
||||
match resolved:
|
||||
case llvmlite.LLVMType.Struct(_, _, _):
|
||||
param_ty = llvmlite.Ptr(pool, resolved)
|
||||
case llvmlite.LLVMType.Array(aelem_ty, _):
|
||||
param_ty = llvmlite.Ptr(pool, aelem_ty)
|
||||
case _:
|
||||
param_ty = resolved
|
||||
if resolved is None:
|
||||
# [S4 fail-fast] 有注解但解析失败:不再静默用 i32
|
||||
# (declare 与 define 签名不一致 → ABI 错位,运行期读栈垃圾)
|
||||
self.Gen.TypeGenErr.fatal_error(
|
||||
arg, f"前向声明形参 '{arg.arg}' 类型注解解析失败", "NameError")
|
||||
return 0
|
||||
# 裸类形参 → Ptr(struct)(对象即指针,与方法形参一致)
|
||||
# CArray 形参 → 元素指针 ty*(C 数组衰减,与 add_param 一致)
|
||||
match resolved:
|
||||
case llvmlite.LLVMType.Struct(_, _, _):
|
||||
param_ty = llvmlite.Ptr(pool, resolved)
|
||||
case llvmlite.LLVMType.Array(aelem_ty, _):
|
||||
param_ty = llvmlite.Ptr(pool, aelem_ty)
|
||||
case _:
|
||||
param_ty = resolved
|
||||
pname: str = pool.alloc(32)
|
||||
if pname is not None:
|
||||
viperlib.snprintf(pname, 32, "%%%s", arg.arg)
|
||||
@@ -623,18 +628,23 @@ class FuncGenDef(CallGenBase.CallGenBase):
|
||||
if arg.annotation is not None:
|
||||
resolved: llvmlite.LLVMType | t.CPtr = self.Gen.TypeGenResolve.resolve_annotation_type(
|
||||
pool, arg.annotation, imported_modules, from_imports, trans, 0)
|
||||
if resolved is not None:
|
||||
# 裸类形参 → Ptr(struct)(对象即指针,与方法形参一致)
|
||||
# CArray 形参 → 元素指针 ty*(C 数组衰减:final(out: t.CArray[..., N])
|
||||
# 的 out 指向调用方数组首元素;传 Ptr(数组) 会使 out[i] 的
|
||||
# GEP 以整个数组为步长错位,摘要垃圾根因)
|
||||
match resolved:
|
||||
case llvmlite.LLVMType.Struct(_, _, _):
|
||||
param_ty = llvmlite.Ptr(pool, resolved)
|
||||
case llvmlite.LLVMType.Array(aelem_ty, _):
|
||||
param_ty = llvmlite.Ptr(pool, aelem_ty)
|
||||
case _:
|
||||
param_ty = resolved
|
||||
if resolved is None:
|
||||
# [S4 fail-fast] 有注解但解析失败:不再静默用 i32
|
||||
# (形参类型错 → ABI 错位/字段访问错)
|
||||
self.Gen.TypeGenErr.fatal_error(
|
||||
arg, f"形参 '{arg.arg}' 类型注解解析失败", "NameError")
|
||||
return 0
|
||||
# 裸类形参 → Ptr(struct)(对象即指针,与方法形参一致)
|
||||
# CArray 形参 → 元素指针 ty*(C 数组衰减:final(out: t.CArray[..., N])
|
||||
# 的 out 指向调用方数组首元素;传 Ptr(数组) 会使 out[i] 的
|
||||
# GEP 以整个数组为步长错位,摘要垃圾根因)
|
||||
match resolved:
|
||||
case llvmlite.LLVMType.Struct(_, _, _):
|
||||
param_ty = llvmlite.Ptr(pool, resolved)
|
||||
case llvmlite.LLVMType.Array(aelem_ty, _):
|
||||
param_ty = llvmlite.Ptr(pool, aelem_ty)
|
||||
case _:
|
||||
param_ty = resolved
|
||||
pname: str = pool.alloc(32)
|
||||
if pname is not None:
|
||||
viperlib.snprintf(pname, 32, "%%%s", arg.arg)
|
||||
|
||||
@@ -861,13 +861,20 @@ class FuncGenMixin(CallGenBase.CallGenBase):
|
||||
#
|
||||
# 用于 nonlocal 共享堆存储分配:数组(如 [4 x i32]=16 字节)不能
|
||||
# 用固定 8 字节(越界写破坏 canary/邻块 → 运行时崩溃,
|
||||
# ClosureTest2 Test 4 非local 数组崩溃根因)。未知类型保守返回 8。
|
||||
# ClosureTest2 Test 4 非local 数组崩溃根因)。
|
||||
#
|
||||
# 注:`case _`(Void/Struct/Func 等)仍返回 8 —— 这不是静默兜底掩盖错误,
|
||||
# 而是**算不出**(结构体尺寸需查布局表,本函数只做 LLVMType 递归);
|
||||
# 改 fatal 会拒绝 "nonlocal 结构体" 这一合法用法,需先补布局查询能力。
|
||||
# ============================================================
|
||||
def _type_byte_size(self, pool: memhub.MemBuddy | t.CPtr,
|
||||
ty: llvmlite.LLVMType | t.CPtr) -> int:
|
||||
"""计算 LLVM 类型占用的字节大小(递归),未知类型返回 8"""
|
||||
"""计算 LLVM 类型占用的字节大小(递归)"""
|
||||
if ty is None:
|
||||
return 8
|
||||
# [S4 fail-fast] 类型缺失 → 不再保守 8 字节(分配不足会越界写邻块)
|
||||
self.Gen.TypeGenErr.fatal_error(
|
||||
None, "nonlocal 共享存储:类型缺失,无法计算尺寸", "TypeError")
|
||||
return 0
|
||||
match ty:
|
||||
case llvmlite.LLVMType.Int(bits):
|
||||
sz_i: int = (bits + 7) // 8
|
||||
|
||||
@@ -47,6 +47,10 @@ class TypeGenCDef(TypeGenBase.TypeGenBase):
|
||||
self.CDefineValues.append(val_buf)
|
||||
else:
|
||||
self.CDefineValues.append("0")
|
||||
# fail-fast:CDefine 值缓冲区分配失败必须终止编译
|
||||
# (与浮点/字符串分支口径一致,不再静默写 "0" 污染常量表)
|
||||
if val_buf is None:
|
||||
self.Gen.TypeGenErr.fatal_error(None, f"CDefine '{name}' 值缓冲区分配失败", "MemoryError")
|
||||
if self.CDefineDoubleFlags is not None:
|
||||
self.CDefineDoubleFlags.append(0)
|
||||
if self.CDefineStrFlags is not None:
|
||||
|
||||
Reference in new issue
Block a user