fix(lsp): 三元表达式按源码顺序遍历

IfExp 原先先走 test 再走 body,生成的 occurrence 顺序与源码相反,body 的 token 被编码器丢弃或产生负增量。改为 body/test/orelse;gate10 增加三元 body 与 else 的跨模块 token/跳转断言。
This commit is contained in:
TermiNexus committed 2026-10-27 17:54:57 +08:00
1 parent b81e4ae3bf
commit ff842e9ff2
3 files changed
+23 -1

No files matched your search

+2 -1
View File
@@ -1377,8 +1377,9 @@ def _WalkExpr(pool: memhub.MemManager*, a: LspAnalysis*, scope: LspScope*,
return
if k == ast.ASTKind.IfExp:
ie: ast.IfExp* = (ast.IfExp*)(node)
_WalkExpr(pool, a, scope, ie.test)
# Source order is `body if test else orelse`; the token stream must stay sorted.
_WalkExpr(pool, a, scope, ie.body)
_WalkExpr(pool, a, scope, ie.test)
_WalkExpr(pool, a, scope, ie.orelse)
return
if k == ast.ASTKind.Dict:
+4
View File
@@ -44,6 +44,10 @@ def reexport_use() -> int:
return gate10_pkg.reexport_fn(1)
def ternary_use(flag: int) -> int:
return extra_fn(EXTRA_CONST) if flag != 0 else extra_fn(EXTRA_CONST + 1)
def else_block(flag: int) -> int:
if flag != 0:
return 1
+17
View File
@@ -1535,6 +1535,23 @@ def gate10(exe: str) -> int:
raise AssertionError(f"package re-export definition failed: {re_def}")
if not re_def[0]["uri"].replace("\\", "/").endswith("gate10_pkg/leaf.vp"):
raise AssertionError(f"package re-export definition is wrong: {re_def}")
for needle, delta, label in (
("return extra_fn(EXTRA_CONST) if", 7, "ternary body"),
("else extra_fn(EXTRA_CONST + 1)", 5, "ternary else"),
):
pos = _position(text, needle)
pos["character"] += delta
if not _find_token(sem_tokens, pos["line"], pos["character"], sem_types.index("function")):
raise AssertionError(f"missing function token in {label}: {pos}")
t_def = client.request(
"textDocument/definition",
{"textDocument": {"uri": uri}, "position": pos},
timeout=120.0,
).get("result")
if not isinstance(t_def, list) or not t_def:
raise AssertionError(f"missing definition in {label}: {t_def}")
if not t_def[0]["uri"].replace("\\", "/").endswith("gate10_extra.vp"):
raise AssertionError(f"wrong definition in {label}: {t_def}")
const_pos = _position(text, "EXTRA_CONST")
if not _find_token_mods(sem_tokens, const_pos["line"], const_pos["character"],
sem_types.index("variable"),