Fix qualified type resolution (#1915)

Fixes an issue where `GetModuleOwnerNode` resolves to levelsUp == 0,
but its enclosing owner is a parse-time invisible scope.
This commit is contained in:
Daniel Chao authored and GitHub committed 2026-10-19 12:23:38 -07:00
1 parent 78c0ebce9d
commit 97c73e7c28
4 files changed
+23 -4

No files matched your search

@@ -24,8 +24,6 @@ public final class GetEnclosingOwnerNode extends ExpressionNode {
public GetEnclosingOwnerNode(int levelsUp) { public GetEnclosingOwnerNode(int levelsUp) {
this.levelsUp = levelsUp; this.levelsUp = levelsUp;
assert levelsUp > 0 : "shouldn't be using GetEnclosingOwnerNode for levelsUp == 0";
} }
public Object executeGeneric(VirtualFrame frame) { public Object executeGeneric(VirtualFrame frame) {
@@ -32,15 +32,21 @@ public final class GetModuleOwnerNode extends ExpressionNode {
CompilerDirectives.transferToInterpreter(); CompilerDirectives.transferToInterpreter();
var levelsUp = -1; var levelsUp = -1;
var skippedInvisibleScopes = false;
for (var current = VmUtils.getOwner(frame); for (var current = VmUtils.getOwner(frame);
current != null; current != null;
current = current.getEnclosingOwner()) { current = current.getEnclosingOwner()) {
if (!current.isParseTimeInvisibleScope()) { if (current.isParseTimeInvisibleScope()) {
skippedInvisibleScopes = true;
} else {
levelsUp += 1; levelsUp += 1;
} }
} }
return replace(levelsUp == 0 ? new GetOwnerNode() : new GetEnclosingOwnerNode(levelsUp)) return replace(
levelsUp == 0 && !skippedInvisibleScopes
? new GetOwnerNode()
: new GetEnclosingOwnerNode(levelsUp))
.executeGeneric(frame); .executeGeneric(frame);
} }
} }
@@ -0,0 +1,12 @@
import "pkl:semver"
local foo = () -> new Dynamic {}
// The `when` predicate is evaluated with the amended function (an invisible scope) as its owner.
local bar = (foo) {
when (new semver.Version {} is semver.Version) {
x = 1
}
}
res = bar.apply()
@@ -0,0 +1,3 @@
res {
x = 1
}