Files
Viper_VRTE/_list.vp
T
TermiNexus 0212bd942c fix(includes): 槽视图改为 cast 到声明类型(地址 → 二级指针不再隐式转换)
【类别 c 源码违规】`slot: <A> = t.CPtr(addr)` 把一级指针(i8*)隐式塞进二级注解
(i8** / X**),违反 2026-09-28 收紧的「指针级数必须相同」。TransPyV 侧 coerce
没有「值侧是显式 cast」豁免(ExprGenBase._ptr_cast_reason 先比层数),故回归测试
在 includes/llvmlite/__function.vp:950 首爆:
  指针隐式转指针已禁止:指针层数不同(源 1 级 → 目标 2 级);源类型 i8* → 目标 i8**。

判据(按注解层数分类,不枚举调用点):
  · str / bytes 本身即 i8*(含一层),再 | t.CPtr ⇒ i8**(槽里存的是 str)
  · str* / bytes* 同 str | t.CPtr(i8**)
  · T | t.CPtr:T 为指针特化时 ⇒ X**(如 list[X*]、list[str])
  · A | t.CPtr | t.CPtr:逐层叠加 ⇒ 二级(如 hashtable 的 value 槽)
  一级注解(int | t.CPtr = i32*、t.CUInt64T | t.CPtr = i64*、类名 | t.CPtr = X*)
  与 i8* 同级且 i8* 是通用指针通配 ⇒ 本可编译,一律保持原样不动。

修法:RHS 改为**cast 到声明类型**,即「注解写什么就 cast 什么」——
  `t.CPtr(addr)` / `(t.CPtr)(addr)` / `rawptr(addr)` → `(A)(addr)`;
  `str*` 注解沿用 sys.vp 既有写法 `str*(addr)`(等价于 `str | t.CPtr` 强转)。
显式写明目标类型后,层数与被指类型均由程序员给出,编译器无需任何豁免。
与 TransPyV/App CallGenCBuiltin.vp 的 `cl_ptr: str | t.CPtr = (str | t.CPtr)(cl_addr)`
以及 includes/vector.vp 的 `dst: T* = (T*)offset` 同一写法。

本仓改动 27 处 / 5 文件:
  _list.vp 7
  _dict.vp 9(8 处槽视图 + L63 的 `key_ptr: str* = rawptr(...)`)
  hashtable.vp 6(含 3 处 …|t.CPtr|t.CPtr)
  llvmlite/__function.vp 2
  mlirlite/__function.vp 3(2 处槽视图 + _mlir_slotp 的 return:该函数返回注解
  即 str | t.CPtr,其 return 同属「i8* → 二级」)

未动其它一级注解站点,例如 _dict.vp 的 int/float/t.CDouble/t.CInt | t.CPtr、
hashtable.vp 的 t.CUInt64T | t.CPtr、argparse.vp:168 的 Argument | t.CPtr。
2026-09-29 15:10:33 +08:00

99 lines
3.7 KiB
Plaintext
Raw 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.
import t, c
import memhub
import string
import stdio
from stdint import *
# [LISTDBG] 诊断(用后移除):list.__init__ 打印初始化结果、append 首次
# (Count==0) 打印 self/Data,配合 CTORDBG 定位二代编 SlotsBugTest cargs(list)
# 头覆盖。默认静默——由命令行 --enable-debug-log 开启(memhub.set_debug_log)
class list[T]:
"""Heap-allocated dynamic list container backed by memhub.MemManager polymorphic allocator.
Usage:
pool: memhub.MemManager = memhub.MemBuddy(arena, arena_size)
nums: list[int] = list[int](pool)
nums.append(42)
x: int = nums.get(0)
For pointer types (e.g. AST | t.CPtr), pass elem_size=8 to avoid object slicing:
lst: list[AST | t.CPtr] = list[AST | t.CPtr](pool, 8)
"""
__data__: t.CPtr
__count__: sizet
__capacity__: sizet
__pool__: rawptr[memhub.MemManager]
__elem_size__: sizet
__iter_index__: sizet
def __new__(self, pool: rawptr[memhub.MemManager], elem_size: sizet = 0):
ret = pool.alloc(48)
return ret
def __init__(self, pool: rawptr[memhub.MemManager], elem_size: sizet = 0):
self.__pool__ = pool
self.__count__ = 0
self.__capacity__ = 8
if elem_size == 0:
self.__elem_size__ = T.__sizeof__()
else:
self.__elem_size__ = elem_size
# 带申请点 tag:本处是"容量 × 元素大小"形态,尺寸为 0 时 [MEM] 报文直接
# 指名本行(pool 是基类指针,故走 memhub.MemAllocTagged)
self.__data__ = memhub.MemAllocTagged(pool, self.__capacity__ * self.__elem_size__,
memhub.DETSITE_LIST_43)
self.__iter_index__ = 0
def __len__(self) -> sizet:
return self.__count__
def append(self, item: T):
if self.__count__ >= self.__capacity__:
new_cap: sizet = self.__capacity__ * 2
new_data: t.CPtr = self.__pool__.alloc(new_cap * self.__elem_size__)
if new_data == None: return
string.memcpy(new_data, self.__data__, self.__count__ * self.__elem_size__)
self.__data__ = new_data
self.__capacity__ = new_cap
elem_ptr: T | t.CPtr = (T | t.CPtr)(t.CUInt64T(self.__data__) + self.__count__ * self.__elem_size__)
elem_ptr[0] = item
self.__count__ += 1
def get(self, index: sizet) -> T:
elem_ptr: T | t.CPtr = (T | t.CPtr)(t.CUInt64T(self.__data__) + index * self.__elem_size__)
return elem_ptr[0]
def __getitem__(self, index: sizet) -> T:
elem_ptr: T | t.CPtr = (T | t.CPtr)(t.CUInt64T(self.__data__) + index * self.__elem_size__)
return elem_ptr[0]
def set(self, index: sizet, value: T):
elem_ptr: T | t.CPtr = (T | t.CPtr)(t.CUInt64T(self.__data__) + index * self.__elem_size__)
elem_ptr[0] = value
def __setitem__(self, index: sizet, value: T):
elem_ptr: T | t.CPtr = (T | t.CPtr)(t.CUInt64T(self.__data__) + index * self.__elem_size__)
elem_ptr[0] = value
def pop(self) -> T:
self.__count__ -= 1
elem_ptr: T | t.CPtr = (T | t.CPtr)(t.CUInt64T(self.__data__) + self.__count__ * self.__elem_size__)
return elem_ptr[0]
def clear(self):
self.__count__ = 0
def __iter__(self) -> list[T] | t.CPtr:
self.__iter_index__ = 0
return self
def __next__(self) -> T:
if self.__iter_index__ >= self.__count__:
raise StopIteration
idx: sizet = self.__iter_index__
self.__iter_index__ = idx + 1
elem_ptr: T | t.CPtr = (T | t.CPtr)(t.CUInt64T(self.__data__) + idx * self.__elem_size__)
return elem_ptr[0]