Skip to content

Commit b1ca110

Browse files
committed
unified: Add getStaticBindingTarget
1 parent 2b28f75 commit b1ca110

5 files changed

Lines changed: 26 additions & 3 deletions

File tree

unified/ql/lib/codeql/Definitions.qll

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ private import codeql.unified.internal.StaticNameBinding
1010
*/
1111
cached
1212
predicate definitionOf(Identifier reference, NameDeclaration definition, string kind) {
13-
reference = trackNameDeclaration(definition).asIdentifier() and
13+
definition = getStaticBindingTarget(reference) and
1414
not reference instanceof NameDeclaration and
1515
kind = "name"
1616
}

unified/ql/lib/codeql/unified/internal/StaticNameBinding.qll

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -640,3 +640,13 @@ class UnqualifiedMemberAccess extends Identifier {
640640
/** Holds if this is an instance access on the accessing class. */
641641
predicate isInstanceAccess() { instanceAccess = true }
642642
}
643+
644+
/** Gets the declaration being accessed by `access`, as determined by static name binding. */
645+
NameDeclaration getStaticBindingTarget(Identifier access) {
646+
// For unqualified accesses, use the shadowing-aware lookup
647+
result = access.(UnqualifiedMemberAccess).getTarget()
648+
or
649+
// For others, just follow the name binding graph
650+
not access instanceof UnqualifiedMemberAccess and
651+
trackNameDeclaration(result).asIdentifier() = access
652+
}
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
private class A {
2+
let x = 123 // name=A.instance.x
3+
4+
func getX() {
5+
return x // $ access=A.instance.x
6+
}
7+
}
8+
9+
private class B : A { // $ access=A
10+
func getX2() {
11+
return x // $ access=A.instance.x
12+
}
13+
}

unified/ql/test/library-tests/static-name-binding/test.ql

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ module StaticDeclAccess implements TestSig {
88

99
predicate hasActualResult(Location location, string element, string tag, string value) {
1010
exists(NameDeclaration decl, Identifier access |
11-
access = trackNameDeclaration(decl).asIdentifier() and
11+
decl = getStaticBindingTarget(access) and
1212
not access instanceof NameDeclaration and
1313
location = access.getLocation() and
1414
element = access.toString() and

unified/ql/test/library-tests/static-name-binding/unqualified-access.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ class ASub : A { // $ access=A
1010

1111
class BSub : B { // $ access=A.B
1212
let x3: B = nil; // $ access=A.B
13-
let x4: C = nil; // $ access=A.B.C SPURIOUS: access=Target3.C // spurious result from folder-based heuristic
13+
let x4: C = nil; // $ access=A.B.C // spurious result from folder-based heuristic
1414
}
1515

1616
class BSub2 : B { // $ access=A.B

0 commit comments

Comments
 (0)