perf(tpc): _MemberSlotAccepts 身份短路 + _generate_structs 热路径局部化(profile 第二梯队)
依据 PROF/main_prof_10152.prof(tottime 2288.9s / 72 文件顺序翻译):
_generate_structs 自身 268.6s cum 1893.2s 15762 基本/35240 总调用
└ 子调用:_TryLoadStructFromStub 1589.5s×418k、_MemberSlotAccepts 61.1s×54.2M
isinstance 39.7s×300M、PointerType 构造 68.7s×15.9M、
SymbolTable.lookup 16.7s×15.9M、__len__ 6.8s×15.9M
本次两处(均等价改写):
1. StructGen._MemberSlotAccepts:在 `Declared == Slot or str(Declared) == str(Slot)`
之前加**身份短路** `Declared is Slot`。该函数被 _generate_structs 调 54.2M 次,
其中 llvmlite `Type.__eq__` 合计 ~30s(types.py:178/303/550/720)+
`str()` ~3.3s;同一对象(body 与 class_members 引用同一类型对象)是其常见形态。
2. StructGen._generate_structs:把 `self.SymbolTable` / `.lookup` 提升为函数级局部
(真值语义逐字保持:SymbolTable 定义了 __len__,故先取 `bool(_symtab)`),
消掉逐类重复的属性查找与 15.9M 次 `__len__`。
说明:本提交只做等价微优化;本函数的大头(35,240 次全量 O(类数×成员数) 扫描、
429k 次结构体 stub 加载、1407 次泛型特化整类发射)需要结构性改动,另行评估。
This commit is contained in:
1 parent
4fc067e3bf
commit
ac0d0f2cc8
1 file changed
+17
-4
@@ -303,6 +303,11 @@ class StructGenMixin:
|
||||
"""
|
||||
if Declared is None or Slot is None:
|
||||
return True
|
||||
# 同一对象直接放行:llvmlite 的 Type.__eq__ 走类型键比较(profile:
|
||||
# 本函数被 _generate_structs 调 54.2M 次,其中 types.py __eq__ 合计 ~30s)
|
||||
# ⇒ 先做身份判定短路,等价且避免绝大多数 __eq__/str() 开销。
|
||||
if Declared is Slot:
|
||||
return True
|
||||
if Declared == Slot or str(Declared) == str(Slot):
|
||||
return True
|
||||
_d_ptr: bool = isinstance(Declared, ir.PointerType)
|
||||
@@ -349,6 +354,14 @@ class StructGenMixin:
|
||||
return False
|
||||
|
||||
def _generate_structs(self) -> None:
|
||||
# 热路径局部化:profile 中本函数被调 35,240 次(cum 1893s),内部
|
||||
# SymbolTable.lookup 15.9M 次(16.7s)+ 真值判断触发的 __len__ 15.9M 次
|
||||
# (6.8s)⇒ 把 SymbolTable / lookup 提到局部,避免逐类重复属性查找。
|
||||
# 真值语义与 `if self.SymbolTable:` 逐字一致(SymbolTable 定义了 __len__,
|
||||
# 空表为假);表在单次调用内只增不减,故提升到函数级等价。
|
||||
_symtab: Any = self.SymbolTable
|
||||
_has_symtab: bool = bool(_symtab)
|
||||
_sym_lookup: Any = _symtab.lookup if _symtab is not None else None
|
||||
all_classes: set[str] = set(self.class_methods.keys()) | set(self.class_members.keys())
|
||||
|
||||
preserved_structs: dict[str, ir.IdentifiedStructType] = {}
|
||||
@@ -367,8 +380,8 @@ class StructGenMixin:
|
||||
all_classes = set(self.class_methods.keys()) | set(self.class_members.keys())
|
||||
for ClassName in all_classes:
|
||||
is_packed: bool = ClassName in self.class_packed
|
||||
if self.SymbolTable:
|
||||
Entry = self.SymbolTable.lookup(ClassName)
|
||||
if _has_symtab and _sym_lookup is not None:
|
||||
Entry = _sym_lookup(ClassName)
|
||||
if Entry and Entry.IsExceptionClass:
|
||||
continue
|
||||
# 注意:类名可能与 CEnum 成员名冲突(如 ASTKind.Module 枚举成员与 Module 类同名)
|
||||
@@ -484,8 +497,8 @@ class StructGenMixin:
|
||||
|
||||
# Step 4: 创建最终的 structs 并设置正确的成员类型
|
||||
for ClassName in all_classes:
|
||||
if self.SymbolTable:
|
||||
Entry = self.SymbolTable.lookup(ClassName)
|
||||
if _has_symtab and _sym_lookup is not None:
|
||||
Entry = _sym_lookup(ClassName)
|
||||
if Entry and Entry.IsExceptionClass:
|
||||
continue
|
||||
# 注意:类名可能与 CEnum 成员名冲突(如 ASTKind.Constant 枚举成员与 Constant 类同名)
|
||||
|
||||
Reference in new issue
Block a user