fix(generic): 修正 SpecToLLVMText 返回值判据倒置,恢复内建标量实参的泛型类型实参推断

_infer_scalar_type_name_from_spec 把 SpecToLLVMText 的『0=成功』误判为失败(写成 == 0 就 return None),使该函数对任何内建标量都恒返回 None —— 泛型函数隐式推断中『实参来自内建标量形参/字段』的路径(Name/Attribute 分支)永远推不出,报『无法从实参推断泛型函数 ... 禁止静默默认 int』(现场:GenericOopTest fxi 体内 fxi2(a, b, ...),a: double)。判据改为 != 0(与 ClassGenVTable 同约定)。

同时收紧位宽映射:i16/i64/f16 在 Viper 没有等位宽裸名别名(裸 int=int32、裸 float=float32),原映射 i16/i64->int、half->float 会静默窄化/扩宽位宽(i64->int 即 i64->i32),违反『禁止静默默认/兜底』原则;改为只映射位宽精确对应的形态(i1->bool、i8->char、i32->int、f32->float、f64->double),其余返回 None 交给调用方 fail-fast 提示显式标注。
This commit is contained in:
TermiNexus committed 2026-10-03 15:28:02 +08:00
1 parent 09ea7283f9
commit bf2f38acd2
1 file changed
+12 -4
+12 -4
View File
@@ -421,21 +421,29 @@ novirtual class ClassGenGeneric(ClassGenBase.ClassGenBase):
(str/char/bytes/bool/float/double 的 SourceName 为 None):按 LLVM
形态映射为源码可解析名(double/float/int/char/bool)。指针/结构体返回
None(交由注解来源名路径处理;此处不做猜测,避免错特化)。
**只映射"位宽精确对应到某个裸名"的形态**(i1→bool、i8→char、i32→int、
f32→float、f64→double)。i16/i64/f16 在 Viper 没有等位宽的裸名别名
(裸 int=int32、裸 float=float32),映射过去会静默窄化/扩宽位宽
(i64→int 即 i64→i32,直接改变 ABI 与数据),违反"禁止静默默认/兜底"
原则 ⇒ 一律返回 None,由调用方汇总后 fail-fast 提示显式标注。
"""
if pool is None or sp is None: return None
buf: str = pool.alloc(32)
if buf is None: return None
buf[0] = '\0'
if TSpec.SpecToLLVMText(sp, buf, 32) == 0:
# SpecToLLVMText 约定 0=成功 / 1=失败(见 TypeSpec.vp 定义与 ClassGenVTable
# 的 `!= 0` 用法):原判据写成 `== 0` 恰好把"成功"当失败返回 None,导致本
# 函数对任何内建标量都恒返回 None —— 泛型函数隐式推断里"实参是内建标量的
# 形参"(如 fxi 体内 fxi2(a, ...),a: double)永远推不出,报
# "无法从实参推断泛型函数 ... 禁止静默默认 int"。
if TSpec.SpecToLLVMText(sp, buf, 32) != 0:
return None
if string.strcmp(buf, "double") == 0: return "double"
if string.strcmp(buf, "float") == 0: return "float"
if string.strcmp(buf, "half") == 0: return "float"
if string.strcmp(buf, "i1") == 0: return "bool"
if string.strcmp(buf, "i8") == 0: return "char"
if string.strcmp(buf, "i16") == 0: return "int"
if string.strcmp(buf, "i32") == 0: return "int"
if string.strcmp(buf, "i64") == 0: return "int"
return None
def _clone_funcdef_for_spec(self, pool: memhub.MemBuddy*,