44
55import unified // reexport in order to shadow e.g. the `TypeParameter` class
66private import unified as Unified
7+ private import TypeMention
78private import TypeInference
89private import codeql.unified.internal.StaticNameBinding
910
@@ -38,12 +39,24 @@ predicate associatedTypeParameterInherited(
3839 name = a .getName ( )
3940}
4041
42+ private predicate isNestedType ( Member m , Identifier nested , ClassLikeDeclaration parent ) {
43+ exists ( parent .getNameNode ( ) ) and
44+ nested = m .getNameNode ( ) and
45+ m = parent .getAMemberIncludingExtensions ( ) and
46+ (
47+ exists ( m .( ClassLikeDeclaration ) .getNameNode ( ) )
48+ or
49+ m instanceof TypeAliasDeclaration
50+ )
51+ }
52+
4153cached
4254newtype TType =
4355 TClassLikeDeclarationType ( ClassLikeDeclaration c ) {
4456 CachedStage:: ref ( ) and
4557 exists ( c .getNameNode ( ) )
4658 } or
59+ TAliasType ( TypeAliasDeclaration alias ) or
4760 TClosureParameterPseudoType ( Parameter p ) {
4861 exists ( FunctionExpr fe |
4962 p = fe .getAParameter ( ) and
@@ -56,6 +69,7 @@ newtype TType =
5669 ) {
5770 associatedTypeParameter ( c , a , inherited )
5871 } or
72+ TParentTypeParameterType ( Member m ) { isNestedType ( m , _, _) } or
5973 TUnknownType ( ) or
6074 TUnknownTypeTypeParameter ( int i ) { i in [ 0 .. 20 ] }
6175
@@ -78,7 +92,14 @@ abstract private class TypeImpl extends TType {
7892 * This includes both positional type parameters and synthetic type parameters,
7993 * such as associated types.
8094 */
81- TypeParameter getATypeParameter ( ) { result = this .getPositionalTypeParameter ( _) }
95+ TypeParameter getATypeParameter ( ) {
96+ result = this .getPositionalTypeParameter ( _)
97+ or
98+ exists ( Member m |
99+ result = TParentTypeParameterType ( m ) and
100+ isNestedType ( m , this .getNameNode ( ) , _)
101+ )
102+ }
82103
83104 /** Gets the name node of this type, if any. */
84105 abstract Identifier getNameNode ( ) ;
@@ -117,11 +138,35 @@ class ClassLikeDeclarationType extends TypeImpl, TClassLikeDeclarationType {
117138 result = TAssociatedTypeParameterType ( c , _, _)
118139 }
119140
120- override string toString ( ) { result = c .getName ( ) }
141+ override string toString ( ) { result = c .getQualifiedName ( ) }
121142
122143 override Location getLocation ( ) { result = c .getLocation ( ) }
123144}
124145
146+ /**
147+ * A type representing a type alias. For type inference, type aliases are expanded,
148+ * but we need them for resolving type mentions.
149+ */
150+ class AliasType extends TypeImpl , TAliasType {
151+ TypeAliasDeclaration alias ;
152+
153+ AliasType ( ) { this = TAliasType ( alias ) }
154+
155+ TypeAliasDeclaration getTypeAliasDeclaration ( ) { result = alias }
156+
157+ TypeMention getAlias ( ) { result = alias .getType ( ) }
158+
159+ override Identifier getNameNode ( ) { result = alias .getNameNode ( ) }
160+
161+ override TypeParameter getPositionalTypeParameter ( int i ) {
162+ result = TTypeParameterType ( alias .getTypeParameter ( i ) )
163+ }
164+
165+ override string toString ( ) { result = alias .getQualifiedName ( ) }
166+
167+ override Location getLocation ( ) { result = alias .getLocation ( ) }
168+ }
169+
125170/**
126171 * A pseudo type that does not correspond to any concrete type in the source code.
127172 */
@@ -165,7 +210,8 @@ abstract class TypeParameter extends TypeImpl {
165210}
166211
167212private class IdAstNode =
168- @unified_type_parameter or @unified_class_like_declaration or @unified_associated_type_declaration;
213+ @unified_type_parameter or @unified_class_like_declaration or
214+ @unified_associated_type_declaration or @unified_member;
169215
170216private predicate id ( IdAstNode x , IdAstNode y ) { x = y }
171217
@@ -217,6 +263,45 @@ class AssociatedTypeParameterType extends TypeParameter, TAssociatedTypeParamete
217263 }
218264}
219265
266+ /**
267+ * A special type parameter used to represent the parent type of a nested class.
268+ *
269+ * For example, for
270+ *
271+ * ```swift
272+ * class Outer<TOuter> {
273+ * class Inner<TInner> {
274+ * }
275+ * }
276+ * ```
277+ *
278+ * the type `Outer<Int>.Inner<String>` is represented as
279+ *
280+ * `TypePath` | `Type`
281+ * ----------------------- | --------
282+ * `""` | `Inner`
283+ * `"TInner"` | `String`
284+ * `"Inner_Parent"` | `Outer`
285+ * `"Inner_Parent.TOuter"` | `Int`
286+ *
287+ * where `Inner_Parent` is one of these type parameters.
288+ */
289+ class ParentTypeParameterType extends TypeParameter , TParentTypeParameterType {
290+ private Member m ;
291+
292+ ParentTypeParameterType ( ) { this = TParentTypeParameterType ( m ) }
293+
294+ ClassLikeDeclaration getParent ( ) { isNestedType ( m , _, result ) }
295+
296+ override Member getDeclaringItem ( ) { result = m }
297+
298+ override Identifier getNameNode ( ) { none ( ) }
299+
300+ override string toString ( ) { result = "(parent:" + m .getNameOrFallback ( ) + ")" }
301+
302+ override Location getLocation ( ) { result = m .getLocation ( ) }
303+ }
304+
220305/**
221306 * A type parameter of the special `UnknownType`.
222307 */
0 commit comments