Skip to content

Commit 2d10f98

Browse files
committed
Unified: Resolve Self in static name binding
1 parent e7c8469 commit 2d10f98

4 files changed

Lines changed: 16 additions & 2 deletions

File tree

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

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,12 @@ class NameBindingPlugin extends Unit {
4242

4343
/** Gets the name of the implicit receiver parameter in `callable`, if it has one. */
4444
string getImplicitReceiverParameterName(Callable callable) { none() }
45+
46+
/**
47+
* Gets the name through which static members of the enclosing class can be
48+
* accessed, for example `Self` in Swift.
49+
*/
50+
string getStaticSelfName() { none() }
4551
}
4652

4753
/** Holds if `member` is an instance member. */

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

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,8 @@ class NameBindingPluginSwift extends NameBindingPlugin {
4444
callable = any(ClassLikeDeclaration cls).getAMember() and
4545
result = "self"
4646
}
47+
48+
override string getStaticSelfName() { result = "Self" }
4749
}
4850

4951
/** Holds if `node` is in a context where a bare name node should be seen as a reference rather than a declaration. */

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

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -210,6 +210,12 @@ predicate storeStep(NameBindingNode node1, string name, NameBindingNode node2) {
210210
)
211211
or
212212
FolderHeuristic::storeStep(node1, name, node2)
213+
or
214+
exists(ClassLikeDeclaration cls |
215+
name = any(NameBindingPlugin p).getStaticSelfName() and
216+
node1.isIdentifier(cls.getNameNode()) and
217+
node2.isStaticMemberNamespace(cls)
218+
)
213219
}
214220

215221
predicate valueStep(NameBindingNode node1, NameBindingNode node2) {

unified/ql/test/library-tests/static-name-binding/explicit-instance-field-access.swift

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ private class A {
88
static let y = 456 // name=A.type.y
99

1010
func getY1() {
11-
return Self.y // $ MISSING: access=A access=A.type.y
11+
return Self.y // $ access=A access=A.type.y
1212
}
1313

1414
static func getY2() {
@@ -30,7 +30,7 @@ private class B : A { // $ access=A
3030
}
3131

3232
func getY3() {
33-
return Self.y // $ MISSING: access=B access=A.type.y
33+
return Self.y // $ access=B access=A.type.y
3434
}
3535

3636
static func getY4() {

0 commit comments

Comments
 (0)