Files
TermiNexus f52fc90221 test(lifetime): 字段逃逸负例从 main 移入普通函数
入口 main 已整体豁免栈逃逸检查(其帧生命期=进程生命期),逃逸写在 main 里会被放行、负向用例失效。改为 CaseField()/CaseAnnField() 承载逃逸、main 调用,保持 P3 规则仍被覆盖。
2026-10-10 14:47:04 +08:00

36 lines
1.5 KiB
Plaintext
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
from stdint import *
# =============================================================================
# 负向工程(**应当编译失败**):P3 —— 禁止把生命期更短的右值赋给生命期更长的左值
#
# §12-P3 的一般规则:右值生命期比目标左值的存储更短 → 报 LifetimeError。
# 本工程是规则点名的实例:`obj.f = &local`
# · 左值 h.p 的存储属于**堆对象**(h 由 `new heap hlife` 得到)→ 活得比本帧长;
# · 右值 &local 是**本帧栈地址**(LIFE_FRAME)→ 出帧即成悬垂指针。
# 期望报错:LifetimeError。
#
# 对照(必须放行,由 --escape 集里的既有正向工程保证不误报):
# · `local_struct.f = &local2`:左值也在本帧(LIFE_FRAME)→ 两者同命,合法;
# · `p = &local`:p 是本帧局部指针槽(LIFE_FRAME)→ 合法。
# 注意 h 必须在**同一个函数**里 `new`,否则它作为形参进来时 Life=UNKNOWN(保守放行)。
# =============================================================================
novirtual class Holder:
p: int*
# 逃逸必须写在**非 main** 函数里:入口 main 现在整体豁免栈逃逸检查
# (其帧生命期 = 进程生命期),写在 main 里会被放行、负向用例失效。
def CaseField() -> int:
h: Holder* = new heap hlife Holder()
local: int = 7
h.p = &local # ← 必须被拒:把本帧栈地址写进堆对象字段
return 0
export def main() -> int:
CaseField()
return 0