refactor: rawptr[T] -> T*(R14)+ 修 REnum 前向占位未就地填充
R14:rawptr[X] -> X*(56 文件 / 834 行改动);保留 6 处 rawptr[t.CPtr](存纯裸指针的规范例外)。 修复:class X(t.REnum) 的变体字段写成自引用 X* 时,字段解析在变体扫描期经 ensure_forward_class 建了一个 opaque 前向占位;末尾 register_struct 按 Ty 指针去重会再建第二个同名 entry,而 find_struct 取首个(占位,0 字段)→ X.__sizeof__() == 0,报「已注册但大小为 0(字段链表未填充)」。改为注册前若命中同模块前向占位则就地填充(与 ensure_forward_class 文档口径一致)。TPC 无此问题,属 TPV 侧缺口。 验证:自举三重重编 SUCCESS;全量 77/77 顺序回归通过(修复前卡在 LLvmLiteTest)。
This commit is contained in:
1 parent
aeb4e8e54c
commit
cd55a7e214
56 files changed
+834
-822
No files matched your search
@@ -32,7 +32,7 @@ import lib.core.Gen.DebugInfoGen as DebugInfoGen
|
||||
|
||||
# _InjectedCreatesCycle - cycle check before auto-injecting a container module
|
||||
# (_list/_dict); a hit (e.g. memhub<->_list) skips injection to avoid a Phase A deadlock.
|
||||
def _InjectedCreatesCycle(entry: rawptr[IncludesScanner.FileEntry], mod_name: str) -> int:
|
||||
def _InjectedCreatesCycle(entry: IncludesScanner.FileEntry*, mod_name: str) -> int:
|
||||
"""Return 1 if injecting mod_name into the current module would create a cycle"""
|
||||
if entry is None or entry.RelPath is None or mod_name is None: return 0
|
||||
inj_sha1: str = StubMergerStore.LookupSha1ByModName(mod_name)
|
||||
@@ -120,7 +120,7 @@ def _RewriteDepsTxt(temp_dir: str, sha1: str, deps_str: str) -> None:
|
||||
td_len: sizet = string.strlen(temp_dir)
|
||||
dpath: str = StubMergerCollect._sliced_path(temp_dir, td_len, sha1, "deps.txt")
|
||||
if dpath is None: return
|
||||
df: rawptr[fileio.File] = fileio.File(dpath, fileio.MODE.W)
|
||||
df: fileio.File* = fileio.File(dpath, fileio.MODE.W)
|
||||
if not df.closed:
|
||||
dl: sizet = string.strlen(deps_str)
|
||||
if dl > 0: df.write(deps_str, dl)
|
||||
@@ -179,12 +179,12 @@ def _BreakContainerCyclesInDeps(temp_dir: str) -> int:
|
||||
|
||||
# _BuildReachableResult - rebuild the reachable FileEntry list from the Sha1Store.
|
||||
# Only incdir-nonempty (includes) entries enter result; App entries would cause duplicate symbols.
|
||||
def _BuildReachableResult(mb: memhub.MemBuddy*, includes_dir: str) -> rawptr[IncludesScanner.ScanResult]:
|
||||
def _BuildReachableResult(mb: memhub.MemBuddy*, includes_dir: str) -> IncludesScanner.ScanResult*:
|
||||
"""Build the reachable FileEntry list from the Sha1Store (reachable includes only)"""
|
||||
if mb is None: return None
|
||||
store_count: sizet = sizet(StubMerger._sha1_store_count)
|
||||
if store_count <= 0 or StubMerger._sha1_store_arr is None: return None
|
||||
result: rawptr[IncludesScanner.ScanResult] = IncludesScanner.create_scan_result(mb)
|
||||
result: IncludesScanner.ScanResult* = IncludesScanner.create_scan_result(mb)
|
||||
if result is None: return None
|
||||
entry_size: sizet = IncludesScanner.FileEntry.__sizeof__()
|
||||
i: sizet
|
||||
@@ -195,7 +195,7 @@ def _BuildReachableResult(mb: memhub.MemBuddy*, includes_dir: str) -> rawptr[Inc
|
||||
iidx: sizet = sizet(i) * StubMerger.MAX_INC_DIR_LEN
|
||||
if StubMerger._sha1_store_incdir[iidx] == '\0': continue
|
||||
eaddr: uint64 = uint64(result.Entries) + uint64(result.Count) * entry_size
|
||||
entry: rawptr[IncludesScanner.FileEntry] = rawptr[IncludesScanner.FileEntry](eaddr)
|
||||
entry: IncludesScanner.FileEntry* = IncludesScanner.FileEntry*(eaddr)
|
||||
if entry is None: continue
|
||||
# Deep-copy SHA1 (store slot is 17 bytes)
|
||||
sha1_buf: bytes = stdlib.malloc(17)
|
||||
@@ -244,7 +244,7 @@ def _BuildReachableResult(mb: memhub.MemBuddy*, includes_dir: str) -> rawptr[Inc
|
||||
|
||||
# ============================================================
|
||||
# RunPhase1 - scan the includes dir; translate and split stubs only when missing.
|
||||
def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawptr[VLogger.Logger]) -> int:
|
||||
def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: VLogger.Logger*) -> int:
|
||||
"""Phase1: scan the includes directory and translate/generate stubs on demand"""
|
||||
if includes_dir is None or temp_dir is None:
|
||||
VLogger.error("includes_dir 或 temp_dir 为空,无法运行 Phase1", "Phase1")
|
||||
@@ -296,7 +296,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
|
||||
# Build the reachable FileEntry list from the Sha1Store; 1a/1b-pre/1b iterate result
|
||||
# (non-empty incdir = includes). use_reachable filtering is idempotent.
|
||||
result: rawptr[IncludesScanner.ScanResult] = _BuildReachableResult(mb, includes_dir)
|
||||
result: IncludesScanner.ScanResult* = _BuildReachableResult(mb, includes_dir)
|
||||
if result is None:
|
||||
VLogger.error("可达 FileEntry 列表构建失败,终止编译", "Phase1")
|
||||
return 1
|
||||
@@ -399,7 +399,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
|
||||
# ============================================================
|
||||
# Phase 1a-pre-generic-all: pre-register all includes' generic templates before mark1.
|
||||
full_scan_g: rawptr[IncludesScanner.ScanResult] = IncludesScanner.scan_includes(mb, includes_dir)
|
||||
full_scan_g: IncludesScanner.ScanResult* = IncludesScanner.scan_includes(mb, includes_dir)
|
||||
if full_scan_g is not None: Phase1Scan._PreRegisterAllGenericTemplates(mb, full_scan_g)
|
||||
else: Phase1Scan._PreRegisterAllGenericTemplates(mb, result)
|
||||
|
||||
@@ -422,7 +422,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
if od_ptr is not None: file_idx = od_ptr[0]
|
||||
|
||||
entry_addr_r: uint64 = uint64(result.Entries) + file_idx * entry_size
|
||||
entry_r: rawptr[IncludesScanner.FileEntry] = rawptr[IncludesScanner.FileEntry](entry_addr_r)
|
||||
entry_r: IncludesScanner.FileEntry* = IncludesScanner.FileEntry*(entry_addr_r)
|
||||
if entry_r is None:
|
||||
p1a_fl += 1
|
||||
continue
|
||||
@@ -448,7 +448,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
|
||||
# Read file contents
|
||||
file_path_r: str = entry_r.Path
|
||||
f_r: rawptr[fileio.File] = fileio.File(file_path_r, fileio.MODE.R)
|
||||
f_r: fileio.File* = fileio.File(file_path_r, fileio.MODE.R)
|
||||
if f_r.closed:
|
||||
p1a_fl += 1
|
||||
continue
|
||||
@@ -492,7 +492,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
t_fa1: uint64 = w32.win32base.GetTickCount64()
|
||||
|
||||
# Create Translator with _declare_only=1 (register struct/enum/union)
|
||||
tr_r: rawptr[HandlesTranslator.Translator] = HandlesTranslator.Translator()
|
||||
tr_r: HandlesTranslator.Translator* = HandlesTranslator.Translator()
|
||||
if tr_r is None:
|
||||
stdlib.free(src_buf_r)
|
||||
p1a_fl += 1
|
||||
@@ -563,7 +563,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
t_pv0: uint64 = w32.win32base.GetTickCount64()
|
||||
for i_pv in range(result.Count):
|
||||
entry_addr_pv: uint64 = uint64(result.Entries) + i_pv * entry_size
|
||||
entry_pv: rawptr[IncludesScanner.FileEntry] = rawptr[IncludesScanner.FileEntry](entry_addr_pv)
|
||||
entry_pv: IncludesScanner.FileEntry* = IncludesScanner.FileEntry*(entry_addr_pv)
|
||||
if entry_pv is None or entry_pv.Sha1 is None:
|
||||
p1bpre_failed += 1
|
||||
continue
|
||||
@@ -578,7 +578,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
p1bpre_failed += 1
|
||||
VLogger.error(f"[Phase 1b-pre] {entry_pv.Path} | vpi 路径生成失败", "Phase1")
|
||||
continue
|
||||
vf_pv: rawptr[fileio.File] = fileio.File(vpi_path_pv, fileio.MODE.R)
|
||||
vf_pv: fileio.File* = fileio.File(vpi_path_pv, fileio.MODE.R)
|
||||
if not vf_pv.closed:
|
||||
vf_pv.close()
|
||||
stdlib.free(vpi_path_pv)
|
||||
@@ -586,7 +586,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
stdlib.free(vpi_path_pv)
|
||||
# Read the file, parse the AST, generate the vpi
|
||||
file_path_pv: str = entry_pv.Path
|
||||
f_pv: rawptr[fileio.File] = fileio.File(file_path_pv, fileio.MODE.R)
|
||||
f_pv: fileio.File* = fileio.File(file_path_pv, fileio.MODE.R)
|
||||
if f_pv.closed:
|
||||
p1bpre_failed += 1
|
||||
VLogger.error(f"[Phase 1b-pre] {file_path_pv} | 无法打开源文件", "Phase1")
|
||||
@@ -634,7 +634,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
if pyi_pos_pv > 0:
|
||||
pyi_path_pv: str = StubMergerCollect._sliced_path(temp_dir, dir_len_pv, sha1_pv, "vpi")
|
||||
if pyi_path_pv is not None:
|
||||
pf_pv: rawptr[fileio.File] = fileio.File(pyi_path_pv, fileio.MODE.W)
|
||||
pf_pv: fileio.File* = fileio.File(pyi_path_pv, fileio.MODE.W)
|
||||
if not pf_pv.closed:
|
||||
pf_pv.write(pyi_buf_pv, pyi_pos_pv)
|
||||
pf_pv.close()
|
||||
@@ -681,7 +681,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
od_ptr_b: t.CPtr = (int*)(od_addr_b)
|
||||
if od_ptr_b is not None: file_idx_b = od_ptr_b[0]
|
||||
entry_addr: uint64 = uint64(result.Entries) + sizet(file_idx_b) * entry_size
|
||||
entry: rawptr[IncludesScanner.FileEntry] = rawptr[IncludesScanner.FileEntry](entry_addr)
|
||||
entry: IncludesScanner.FileEntry* = IncludesScanner.FileEntry*(entry_addr)
|
||||
if entry is None:
|
||||
failed += 1
|
||||
continue
|
||||
@@ -714,7 +714,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
force_translate: int = 0
|
||||
vpi_path_1b: str = StubMergerCollect._sliced_path(temp_dir, dir_len, sha1, "vpi")
|
||||
if vpi_path_1b is not None:
|
||||
vf_1b: rawptr[fileio.File] = fileio.File(vpi_path_1b, fileio.MODE.R)
|
||||
vf_1b: fileio.File* = fileio.File(vpi_path_1b, fileio.MODE.R)
|
||||
if not vf_1b.closed:
|
||||
vbuf_1b: bytes = stdlib.malloc(1048576)
|
||||
if vbuf_1b is not None:
|
||||
@@ -743,13 +743,13 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
VLogger.info(f"含 class 定义,强制翻译: {rp}(sha1={sha1})", "Phase1")
|
||||
else:
|
||||
# Skip already-existing stubs (on-demand translation)
|
||||
sf: rawptr[fileio.File] = fileio.File(stub_path, fileio.MODE.R)
|
||||
sf: fileio.File* = fileio.File(stub_path, fileio.MODE.R)
|
||||
if not sf.closed:
|
||||
sf.close()
|
||||
# Check that text.ll exists too (vtable scan needs it)
|
||||
text_path: str = StubMergerCollect._sliced_path(temp_dir, dir_len, sha1, "text.ll")
|
||||
if text_path is not None:
|
||||
tf: rawptr[fileio.File] = fileio.File(text_path, fileio.MODE.R)
|
||||
tf: fileio.File* = fileio.File(text_path, fileio.MODE.R)
|
||||
if not tf.closed:
|
||||
tf.close()
|
||||
# The sidecar ({sha1}.meta) and online FULL artifact ({sha1}.full.ll) must also exist;
|
||||
@@ -757,7 +757,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
meta_path_1b: str = StubMergerCollect._sliced_path(temp_dir, dir_len, sha1, "meta")
|
||||
meta_ok_1b: int = 0
|
||||
if meta_path_1b is not None:
|
||||
mf_chk: rawptr[fileio.File] = fileio.File(meta_path_1b, fileio.MODE.R)
|
||||
mf_chk: fileio.File* = fileio.File(meta_path_1b, fileio.MODE.R)
|
||||
if not mf_chk.closed:
|
||||
mf_chk.close()
|
||||
meta_ok_1b = 1
|
||||
@@ -765,7 +765,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
full_path_1b: str = StubMergerCollect._sliced_path(temp_dir, dir_len, sha1, "full.ll")
|
||||
full_ok_1b: int = 0
|
||||
if full_path_1b is not None:
|
||||
ff_chk: rawptr[fileio.File] = fileio.File(full_path_1b, fileio.MODE.R)
|
||||
ff_chk: fileio.File* = fileio.File(full_path_1b, fileio.MODE.R)
|
||||
if not ff_chk.closed:
|
||||
ff_chk.close()
|
||||
full_ok_1b = 1
|
||||
@@ -790,7 +790,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
|
||||
# Read file contents
|
||||
file_path: str = entry.Path
|
||||
f: rawptr[fileio.File] = fileio.File(file_path, fileio.MODE.R)
|
||||
f: fileio.File* = fileio.File(file_path, fileio.MODE.R)
|
||||
if f is None:
|
||||
VLogger.error(f"无法打开(f=None): {file_path}", "Phase1")
|
||||
failed += 1
|
||||
@@ -850,7 +850,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
# is only a fallback when the vpi is missing.
|
||||
vpi_path_1b: str = StubMergerCollect._sliced_path(temp_dir, dir_len, sha1, "vpi")
|
||||
if vpi_path_1b is not None:
|
||||
vf_1b: rawptr[fileio.File] = fileio.File(vpi_path_1b, fileio.MODE.R)
|
||||
vf_1b: fileio.File* = fileio.File(vpi_path_1b, fileio.MODE.R)
|
||||
vpi_exists_1b: int = 0
|
||||
if not vf_1b.closed:
|
||||
vf_1b.close()
|
||||
@@ -860,7 +860,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
if pyi_buf is not None:
|
||||
pyi_pos: sizet = StubConverter._GeneratePyiFromAst(mb, tree, entry.Path, pyi_buf, Phase1.PYI_BUF_SIZE)
|
||||
if pyi_pos > 0:
|
||||
pf_1b: rawptr[fileio.File] = fileio.File(vpi_path_1b, fileio.MODE.W)
|
||||
pf_1b: fileio.File* = fileio.File(vpi_path_1b, fileio.MODE.W)
|
||||
if not pf_1b.closed:
|
||||
pf_1b.write(pyi_buf, pyi_pos)
|
||||
pf_1b.close()
|
||||
@@ -868,7 +868,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
stdlib.free(vpi_path_1b)
|
||||
|
||||
# Translate AST -> LLVM IR
|
||||
tr: rawptr[HandlesTranslator.Translator] = HandlesTranslator.Translator()
|
||||
tr: HandlesTranslator.Translator* = HandlesTranslator.Translator()
|
||||
if tr is None:
|
||||
stdlib.free(src_buf)
|
||||
failed += 1
|
||||
@@ -934,7 +934,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
dir_len_p1: sizet = string.strlen(temp_dir)
|
||||
stub_path_p1: str = StubMergerCollect._sliced_path(temp_dir, dir_len_p1, sha1, "stub.ll")
|
||||
if stub_path_p1 is not None:
|
||||
sf_p1: rawptr[fileio.File] = fileio.File(stub_path_p1, fileio.MODE.W)
|
||||
sf_p1: fileio.File* = fileio.File(stub_path_p1, fileio.MODE.W)
|
||||
if not sf_p1.closed:
|
||||
sf_p1.write(stub_buf, stub_len)
|
||||
sf_p1.close()
|
||||
@@ -955,7 +955,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
# save text.ll
|
||||
text_path_p1: str = StubMergerCollect._sliced_path(temp_dir, dir_len_p1, sha1, "text.ll")
|
||||
if text_path_p1 is not None:
|
||||
tf_p1: rawptr[fileio.File] = fileio.File(text_path_p1, fileio.MODE.W)
|
||||
tf_p1: fileio.File* = fileio.File(text_path_p1, fileio.MODE.W)
|
||||
if not tf_p1.closed:
|
||||
tf_p1.write(text_buf, text_len)
|
||||
tf_p1.close()
|
||||
@@ -973,7 +973,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
full_len_p1: sizet = string.strlen(full_buf_p1)
|
||||
full_path_p1: str = StubMergerCollect._sliced_path(temp_dir, dir_len_p1, sha1, "full.ll")
|
||||
if full_path_p1 is not None:
|
||||
ff_p1: rawptr[fileio.File] = fileio.File(full_path_p1, fileio.MODE.W)
|
||||
ff_p1: fileio.File* = fileio.File(full_path_p1, fileio.MODE.W)
|
||||
if not ff_p1.closed:
|
||||
ff_p1.write(full_buf_p1, full_len_p1)
|
||||
ff_p1.close()
|
||||
@@ -995,7 +995,7 @@ def RunPhase1(mb: memhub.MemBuddy*, includes_dir: str, temp_dir: str, log: rawpt
|
||||
# save dependencies(_imported_modules) for Phase B
|
||||
deps_path_p1: str = StubMergerCollect._sliced_path(temp_dir, dir_len_p1, sha1, "deps.txt")
|
||||
if deps_path_p1 is not None:
|
||||
df_p1: rawptr[fileio.File] = fileio.File(deps_path_p1, fileio.MODE.W)
|
||||
df_p1: fileio.File* = fileio.File(deps_path_p1, fileio.MODE.W)
|
||||
if not df_p1.closed:
|
||||
if tr._imported_modules is not None:
|
||||
dl: sizet = string.strlen(tr._imported_modules)
|
||||
|
||||
Reference in new issue
Block a user