@@ -16,6 +16,11 @@ import dotty.tools.dotc.typer.ImportInfo
16
16
import dotty .tools .dotc .util .Property
17
17
import dotty .tools .dotc .transform .CheckUnused .UnusedData .UnusedResult
18
18
import dotty .tools .dotc .core .Mode
19
+ import dotty .tools .dotc .core .Types .TypeTraverser
20
+ import dotty .tools .dotc .core .Types .Type
21
+ import dotty .tools .dotc .core .Types .AnnotatedType
22
+ import dotty .tools .dotc .core .Flags .flagsString
23
+ import dotty .tools .dotc .core .Flags
19
24
20
25
21
26
@@ -64,13 +69,14 @@ class CheckUnused extends Phase:
64
69
tree match
65
70
case imp: tpd.Import =>
66
71
unusedDataApply(_.registerImport(imp))
72
+ traverseChildren(tree)(using newCtx)
67
73
case ident : Ident =>
68
74
unusedDataApply(_.registerUsed(ident.symbol))
69
75
traverseChildren(tree)(using newCtx)
70
76
case sel : Select =>
71
77
unusedDataApply(_.registerUsed(sel.symbol))
72
78
traverseChildren(tree)(using newCtx)
73
- case _ : (tpd.Block | tpd.Template ) =>
79
+ case _ : (tpd.Block | tpd.Template | tpd. PackageDef ) =>
74
80
unusedDataApply { ud =>
75
81
ud.inNewScope(ScopeType .fromTree(tree))(traverseChildren(tree)(using newCtx))
76
82
}
@@ -83,11 +89,19 @@ class CheckUnused extends Phase:
83
89
case t : tpd.Bind =>
84
90
unusedDataApply(_.registerPatVar(t))
85
91
traverseChildren(tree)(using newCtx)
92
+ case t@ tpd.TypeTree () =>
93
+ typeTraverser(unusedDataApply).traverse(t.tpe)
94
+ traverseChildren(tree)(using newCtx)
86
95
case _ =>
87
96
traverseChildren(tree)(using newCtx)
88
97
end traverse
89
98
end traverser
90
99
100
+ private def typeTraverser (dt : (UnusedData => Any ) => Unit )(using Context ) = new TypeTraverser :
101
+ override def traverse (tp : Type ): Unit = tp match
102
+ case AnnotatedType (_, annot) => dt(_.registerUsed(annot.symbol))
103
+ case _ => traverseChildren(tp)
104
+
91
105
private def reportUnused (res : UnusedData .UnusedResult )(using Context ): Unit =
92
106
import CheckUnused .WarnTypes
93
107
res.warnings.foreach { s =>
@@ -185,6 +199,8 @@ object CheckUnused:
185
199
if ! isConstructorOfSynth(sym) then
186
200
usedInScope.top += sym -> sym.isAccessibleAsIdent
187
201
usedDef += sym
202
+ if sym.isConstructor && sym.exists then
203
+ registerUsed(sym.owner) // constructor are "implicitly" imported with the class
188
204
189
205
/** Register a list of found (used) symbols */
190
206
def registerUsed (syms : Seq [Symbol ])(using Context ): Unit =
@@ -340,10 +356,10 @@ object CheckUnused:
340
356
/** Given an import and accessibility, return an option of selector that match import<->symbol */
341
357
def isInImport (imp : tpd.Import , isAccessible : Boolean )(using Context ): Option [ImportSelector ] =
342
358
val tpd .Import (qual, sels) = imp
343
- val qualHasSymbol = qual.tpe.member(sym.name).symbol == sym
359
+ val qualHasSymbol = qual.tpe.member(sym.name).alternatives.map(_. symbol).contains( sym)
344
360
def selector = sels.find(sel => sel.name.toTermName == sym.name || sel.name.toTypeName == sym.name)
345
361
def wildcard = sels.find(sel => sel.isWildcard && ((sym.is(Given ) == sel.isGiven) || sym.is(Implicit )))
346
- if qualHasSymbol && ! isAccessible then
362
+ if qualHasSymbol && ! isAccessible && sym.exists then
347
363
selector.orElse(wildcard) // selector with name or wildcard (or given)
348
364
else
349
365
None
0 commit comments