Skip to content

[WIP] Safe initialization for Scala #4543

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
wants to merge 83 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
83 commits
Select commit Hold shift + click to select a range
dc27664
Add tests and implementation
liufengyun May 2, 2018
8054290
Supress warnings for default values
liufengyun Oct 5, 2018
f3242c7
Support super
liufengyun Oct 5, 2018
2b626a8
Tweak check conditions
liufengyun Oct 8, 2018
9378a9f
Prepare tests for V3
liufengyun Oct 18, 2018
a92aaaf
Support call methods that are called in parents
liufengyun Oct 18, 2018
8961a31
WIP - handle abstract fields
liufengyun Oct 22, 2018
a9d9b86
overridding tests pass
liufengyun Oct 22, 2018
fcad3cd
WIP
liufengyun Oct 23, 2018
3143956
Don't make methods called in parent callable in child
liufengyun Oct 24, 2018
2eff27c
Infer @init for called methods with full result
liufengyun Oct 24, 2018
902faeb
Record dynamic calls for @init methods
liufengyun Oct 24, 2018
7bffbd3
Fix partial value annotation
liufengyun Oct 24, 2018
227eab7
Refactor code
liufengyun Oct 24, 2018
f66de89
Rename partial to raw
liufengyun Oct 24, 2018
9423e21
Rename raw to cold
liufengyun Oct 24, 2018
51f3aff
Change filled to warm
liufengyun Oct 24, 2018
efb8395
Rename full to hot
liufengyun Oct 24, 2018
c88dab2
Refactor signature of widen
liufengyun Oct 24, 2018
ab33a92
Rename BlankValue to IcyValue
liufengyun Oct 24, 2018
93c90ca
WIP - refactor widen
liufengyun Oct 24, 2018
418c37f
Refactor sym.isCold and sym.isWarm
liufengyun Oct 24, 2018
8e500ce
Make WarmValue condition on dependencies
liufengyun Oct 24, 2018
079e9b4
Leak warm objects as cold
liufengyun Oct 24, 2018
9a882ec
Prevent leak of icy objects
liufengyun Oct 24, 2018
63c5d1f
WIP - scaffold for capture analysis
liufengyun Oct 24, 2018
3568ec4
WIP - initial capture analysis
liufengyun Oct 25, 2018
ef3a647
WIP - capture analysis proto works
liufengyun Oct 25, 2018
70645ce
Widening of trees works
liufengyun Oct 25, 2018
36eaa78
Only allow hot values travel through dynamic calls
liufengyun Oct 25, 2018
8d97c07
Fix param checking of dynamic methods
liufengyun Oct 25, 2018
5ed4332
Check overriding of class parameters
liufengyun Oct 26, 2018
3200280
Don't warn when select a registered dynamic call
liufengyun Oct 26, 2018
531baea
Refine dynamic call annotations
liufengyun Oct 26, 2018
2bd5f82
Check inner class annotation in parents
liufengyun Oct 26, 2018
59a8324
Don't annotate method call on selection error
liufengyun Oct 26, 2018
8024805
Try widen conditional value
liufengyun Oct 26, 2018
75f7f25
Refactor widening of SliceRep
liufengyun Oct 26, 2018
67effb8
Treat self as ColdValue
liufengyun Oct 29, 2018
f0ea2b5
Support calling abstract methods from parent
liufengyun Oct 29, 2018
0d652a9
Use @icy for icy methods
liufengyun Oct 29, 2018
b0239de
WIP - fix infinite loop in widening
liufengyun Oct 29, 2018
d0856f5
WIP - fix exception in widening
liufengyun Oct 31, 2018
0e5b913
Allow select on abstract methods
liufengyun Oct 31, 2018
7ca3a04
Check capturing of TypeRef in New
liufengyun Nov 1, 2018
6d60f5e
Introduce class values
liufengyun Nov 1, 2018
00ff986
Auto infer @init of inner class
liufengyun Nov 1, 2018
61e8de3
No blow up for Flags
liufengyun Nov 1, 2018
9dd7790
Force lazy value but not update during widening
liufengyun Nov 1, 2018
45fd3ab
Add tests for local classes
liufengyun Nov 1, 2018
9632897
Disallow override called in class body
liufengyun Nov 2, 2018
99c3177
Add tests for field overriding
liufengyun Nov 2, 2018
c507868
More friendly message when collapsing errors from call
liufengyun Nov 2, 2018
bdadd8a
Separate type and term symbols in environment
liufengyun Nov 2, 2018
9c82127
Fix exception in self selection
liufengyun Nov 2, 2018
4dda94a
Fix exception for generics
liufengyun Nov 2, 2018
f7f9198
Fix exception for joining ClassValue
liufengyun Nov 2, 2018
3810c3a
Infer @init for lazy fields
liufengyun Nov 5, 2018
b3fa1a4
Use widening mode for checking @init: no dynamic call allowed
liufengyun Nov 5, 2018
22ee973
Report errors in select
liufengyun Nov 5, 2018
1925f2c
Recheck annotations when instantiating inner/local classes
liufengyun Nov 5, 2018
5d41c1a
Remove WarmValue.dynamic
liufengyun Nov 6, 2018
9bdef31
Allow access called abstract methods in init methods
liufengyun Nov 6, 2018
46dfd3e
Don't warm for overriding abstract field with cold value
liufengyun Nov 6, 2018
9961e32
Fix exception in capture analysis
liufengyun Nov 7, 2018
3dc5fab
Ignore ordering of inferrence
liufengyun Nov 7, 2018
ca7b52e
Allow access to ParamAccessor
liufengyun Nov 7, 2018
9149523
Move ParamAccessor override check
liufengyun Nov 7, 2018
d7e19e4
Fix exception in assigning to self required type
liufengyun Nov 7, 2018
6c04901
More friendly capture information in error message
liufengyun Nov 7, 2018
c41b389
Refine widening
liufengyun Nov 7, 2018
653d05b
Fix capture and mixin implementation check
liufengyun Nov 8, 2018
809955b
Add more capture tests
liufengyun Nov 8, 2018
e95a1e4
Cache of widened value
liufengyun Nov 8, 2018
4969adb
Add more exception tests
liufengyun Nov 8, 2018
0b6563f
More friendly capture warning
liufengyun Nov 8, 2018
36306ba
Fix exception in selecting abstract
liufengyun Nov 8, 2018
1aa7047
Fix exception by refactoring setting mode
liufengyun Nov 8, 2018
2ef8877
Add more mixin tests
liufengyun Nov 9, 2018
c7ce7fb
Propagation of init method dependencies
liufengyun Nov 9, 2018
fd15e3a
Fix rebase errors
liufengyun Nov 9, 2018
a2eb552
Add more init tests
liufengyun Nov 9, 2018
2d90d74
Bootstrap v3
liufengyun Nov 9, 2018
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions compiler/src/dotty/tools/dotc/Compiler.scala
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ class Compiler {
List(new sbt.ExtractDependencies) :: // Sends information on classes' dependencies to sbt via callbacks
List(new PostTyper) :: // Additional checks and cleanups after type checking
List(new sbt.ExtractAPI) :: // Sends a representation of the API of classes to sbt via callbacks
List(new init.Checker) :: // Check safe initialization of class fields
Nil

/** Phases dealing with TASTY tree pickling and unpickling */
Expand Down
3 changes: 3 additions & 0 deletions compiler/src/dotty/tools/dotc/Driver.scala
Original file line number Diff line number Diff line change
Expand Up @@ -40,10 +40,13 @@ class Driver {
}
else ctx.reporter

@scala.annotation.init
protected def initCtx: Context = (new ContextBase).initialCtx

@scala.annotation.init
protected def sourcesRequired: Boolean = true

@scala.annotation.init
def setup(args: Array[String], rootCtx: Context): (List[String], Context) = {
val ctx = rootCtx.fresh
val summary = CompilerCommand.distill(args)(ctx)
Expand Down
2 changes: 1 addition & 1 deletion compiler/src/dotty/tools/dotc/Run.scala
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,7 @@ class Run(comp: Compiler, ictx: Context) extends ImplicitRunInfo with Constraint
ctx.initialize()(start) // re-initialize the base context with start
def addImport(ctx: Context, refFn: () => TermRef) =
ctx.fresh.setImportInfo(ImportInfo.rootImport(refFn)(ctx))
(start.setRun(this) /: defn.RootImportFns)(addImport)
(start.setRun(this: @unchecked) /: defn.RootImportFns)(addImport)
}

private[this] var compiling = false
Expand Down
2 changes: 1 addition & 1 deletion compiler/src/dotty/tools/dotc/ast/DesugarEnums.scala
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ object DesugarEnums {
import untpd._

@sharable object CaseKind extends Enumeration {
val Simple, Object, Class: Value = Value
val Simple, Object, Class: Value = Value : @unchecked
}

/** Attachment containing the number of enum cases and the smallest kind that was seen so far. */
Expand Down
6 changes: 4 additions & 2 deletions compiler/src/dotty/tools/dotc/ast/TreeInfo.scala
Original file line number Diff line number Diff line change
Expand Up @@ -559,14 +559,16 @@ trait TypedTreeInfo extends TreeInfo[Type] { self: Trees.Instance[Type] =>
*
* Note: targ and vargss may be empty
*/
def decomposeCall(tree: Tree): (Tree, List[Tree], List[List[Tree]]) = {
@tailrec
def decomposeCall(tree: Tree)(implicit ctx: Context): (Tree, List[Tree], List[List[Tree]]) = {
def loop(tree: Tree, targss: List[Tree], argss: List[List[Tree]]): (Tree, List[Tree], List[List[Tree]]) =
tree match {
case Apply(fn, args) =>
loop(fn, targss, args :: argss)
case TypeApply(fn, targs) =>
loop(fn, targs ::: targss, argss)
case Block(stats, expr) =>
val (fn, targss2, argss2) = loop(expr, targss, argss)
(Block(stats, fn), targss2, argss2)
case _ =>
(tree, targss, argss)
}
Expand Down
2 changes: 1 addition & 1 deletion compiler/src/dotty/tools/dotc/ast/Trees.scala
Original file line number Diff line number Diff line change
Expand Up @@ -804,7 +804,7 @@ object Trees {
trees foreach (_.foreachInThicket(op))
}

class EmptyValDef[T >: Untyped] extends ValDef[T](
final class EmptyValDef[T >: Untyped] extends ValDef[T](
nme.WILDCARD, genericEmptyTree[T], genericEmptyTree[T]) with WithoutTypeOrPos[T] {
myTpe = NoType.asInstanceOf[T]
override def isEmpty: Boolean = true
Expand Down
1 change: 1 addition & 0 deletions compiler/src/dotty/tools/dotc/config/Printers.scala
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ object Printers {
val exhaustivity: Printer = noPrinter
val gadts: Printer = noPrinter
val hk: Printer = noPrinter
val init: Printer = noPrinter
val implicits: Printer = noPrinter
val implicitsDetailed: Printer = noPrinter
val inlining: Printer = noPrinter
Expand Down
13 changes: 13 additions & 0 deletions compiler/src/dotty/tools/dotc/config/Settings.scala
Original file line number Diff line number Diff line change
Expand Up @@ -255,45 +255,58 @@ object Settings {
def processArguments(arguments: List[String], processAll: Boolean)(implicit ctx: Context): ArgsSummary =
processArguments(ArgsSummary(ctx.settingsState, arguments, Nil, Nil), processAll, Nil)

@scala.annotation.init
def publish[T](settingf: Int => Setting[T]): Setting[T] = {
val setting = settingf(_allSettings.length)
_allSettings += setting
setting
}

@scala.annotation.init
def BooleanSetting(name: String, descr: String, initialValue: Boolean = false): Setting[Boolean] =
publish(Setting(name, descr, initialValue))

@scala.annotation.init
def StringSetting(name: String, helpArg: String, descr: String, default: String): Setting[String] =
publish(Setting(name, descr, default, helpArg))

@scala.annotation.init
def ChoiceSetting(name: String, helpArg: String, descr: String, choices: List[String], default: String): Setting[String] =
publish(Setting(name, descr, default, helpArg, choices))

@scala.annotation.init
def IntSetting(name: String, descr: String, default: Int, range: Seq[Int] = Nil): Setting[Int] =
publish(Setting(name, descr, default, choices = range))

@scala.annotation.init
def MultiStringSetting(name: String, helpArg: String, descr: String): Setting[List[String]] =
publish(Setting(name, descr, Nil, helpArg))

@scala.annotation.init
def OutputSetting(name: String, helpArg: String, descr: String, default: AbstractFile): Setting[AbstractFile] =
publish(Setting(name, descr, default, helpArg))

@scala.annotation.init
def PathSetting(name: String, descr: String, default: String): Setting[String] =
publish(Setting(name, descr, default))

@scala.annotation.init
def PathSetting(name: String, helpArg: String, descr: String, default: String): Setting[String] =
publish(Setting(name, descr, default, helpArg))

@scala.annotation.init
def PhasesSetting(name: String, descr: String, default: String = ""): Setting[List[String]] =
publish(Setting(name, descr, if (default.isEmpty) Nil else List(default)))

@scala.annotation.init
def PrefixSetting(name: String, pre: String, descr: String): Setting[List[String]] =
publish(Setting(name, descr, Nil, prefix = pre))

@scala.annotation.init
def VersionSetting(name: String, descr: String, default: ScalaVersion = NoScalaVersion): Setting[ScalaVersion] =
publish(Setting(name, descr, default))

@scala.annotation.init
def OptionSetting[T: ClassTag](name: String, descr: String): Setting[Option[T]] =
publish(Setting(name, descr, None, propertyClass = Some(implicitly[ClassTag[T]].runtimeClass)))
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ trait WrappedProperties extends PropertiesTrait {
def wrap[T](body: => T): Option[T]

protected def propCategory: String = "wrapped"
protected def pickJarBasedOn: Class[_] = this.getClass
protected def pickJarBasedOn: Class[_] = this.getClass: @unchecked

override def propIsSet(name: String): Boolean = wrap(super.propIsSet(name)) exists (x => x)
override def propOrElse(name: String, alt: String): String = wrap(super.propOrElse(name, alt)) getOrElse alt
Expand Down
16 changes: 16 additions & 0 deletions compiler/src/dotty/tools/dotc/core/Annotations.scala
Original file line number Diff line number Diff line change
Expand Up @@ -177,6 +177,22 @@ object Annotations {
else None
}

/** Extractor for init annotations */
object Call {
/** A regular, non-deferred Child annotation */
def apply(sym: Symbol)(implicit ctx: Context): Annotation = {
val tree = New(defn.CallAnnotType.appliedTo(sym.owner.thisType.select(sym.name, sym)), Nil)
ConcreteAnnotation(tree)
}

def unapply(ann: Annotation)(implicit ctx: Context): Option[Symbol] =
if (ann.symbol == defn.CallAnnot) {
val AppliedType(tycon, (arg: NamedType) :: Nil) = ann.tree.tpe
Some(arg.symbol)
}
else None
}

def makeSourceFile(path: String)(implicit ctx: Context): Annotation =
apply(defn.SourceFileAnnot, Literal(Constant(path)))
}
Expand Down
24 changes: 19 additions & 5 deletions compiler/src/dotty/tools/dotc/core/Contexts.scala
Original file line number Diff line number Diff line change
Expand Up @@ -89,11 +89,13 @@ object Contexts {

/** The outer context */
private[this] var _outer: Context = _
@scala.annotation.init
protected def outer_=(outer: Context): Unit = _outer = outer
def outer: Context = _outer

/** The current context */
private[this] var _period: Period = _
@scala.annotation.init
protected def period_=(period: Period): Unit = {
assert(period.firstPhaseId == period.lastPhaseId, period)
_period = period
Expand All @@ -102,53 +104,63 @@ object Contexts {

/** The scope nesting level */
private[this] var _mode: Mode = _
@scala.annotation.init
protected def mode_=(mode: Mode): Unit = _mode = mode
def mode: Mode = _mode

/** The current owner symbol */
private[this] var _owner: Symbol = _
@scala.annotation.init
protected def owner_=(owner: Symbol): Unit = _owner = owner
def owner: Symbol = _owner

/** The current tree */
private[this] var _tree: Tree[_ >: Untyped]= _
@scala.annotation.init
protected def tree_=(tree: Tree[_ >: Untyped]): Unit = _tree = tree
def tree: Tree[_ >: Untyped] = _tree

/** The current scope */
private[this] var _scope: Scope = _
@scala.annotation.init
protected def scope_=(scope: Scope): Unit = _scope = scope
def scope: Scope = _scope

/** The current type comparer */
private[this] var _typerState: TyperState = _
@scala.annotation.init
protected def typerState_=(typerState: TyperState): Unit = _typerState = typerState
def typerState: TyperState = _typerState

/** The current type assigner or typer */
private[this] var _typeAssigner: TypeAssigner = _
@scala.annotation.init
protected def typeAssigner_=(typeAssigner: TypeAssigner): Unit = _typeAssigner = typeAssigner
def typeAssigner: TypeAssigner = _typeAssigner

/** The currently active import info */
private[this] var _importInfo: ImportInfo = _
@scala.annotation.init
protected def importInfo_=(importInfo: ImportInfo): Unit = _importInfo = importInfo
def importInfo: ImportInfo = _importInfo

/** The current bounds in force for type parameters appearing in a GADT */
private[this] var _gadt: GADTMap = _
@scala.annotation.init
protected def gadt_=(gadt: GADTMap): Unit = _gadt = gadt
def gadt: GADTMap = _gadt

/** The history of implicit searches that are currently active */
private[this] var _searchHistory: SearchHistory = null
@scala.annotation.init
protected def searchHistory_= (searchHistory: SearchHistory): Unit = _searchHistory = searchHistory
def searchHistory: SearchHistory = _searchHistory

/** The current type comparer. This ones updates itself automatically for
* each new context.
*/
private[this] var _typeComparer: TypeComparer = _
@scala.annotation.init
protected def typeComparer_=(typeComparer: TypeComparer): Unit = _typeComparer = typeComparer
def typeComparer: TypeComparer = {
if (_typeComparer.ctx ne this)
Expand All @@ -160,6 +172,7 @@ object Contexts {
* Typically used for attributes that are read and written only in special situations.
*/
private[this] var _moreProperties: Map[Key[Any], Any] = _
@scala.annotation.init
protected def moreProperties_=(moreProperties: Map[Key[Any], Any]): Unit = _moreProperties = moreProperties
def moreProperties: Map[Key[Any], Any] = _moreProperties

Expand All @@ -172,6 +185,7 @@ object Contexts {
* slightly slower than a normal field access would be.
*/
private var _store: Store = _
@scala.annotation.init
protected def store_=(store: Store): Unit = _store = store
def store: Store = _store

Expand Down Expand Up @@ -219,7 +233,7 @@ object Contexts {
else
outer.implicits
if (implicitRefs.isEmpty) outerImplicits
else new ContextualImplicits(implicitRefs, outerImplicits)(this)
else new ContextualImplicits(implicitRefs, outerImplicits)(this: @unchecked)
}
implicitsCache
}
Expand Down Expand Up @@ -544,7 +558,7 @@ object Contexts {
/** A class defining the initial context with given context base
* and set of possible settings.
*/
private class InitialContext(val base: ContextBase, settingsGroup: SettingGroup) extends FreshContext {
private class InitialContext(val base: ContextBase @scala.annotation.cold, settingsGroup: SettingGroup) extends FreshContext {
outer = NoContext
period = InitialPeriod
mode = Mode.None
Expand All @@ -554,14 +568,14 @@ object Contexts {
typeAssigner = TypeAssigner
moreProperties = Map.empty
store = initialStore.updated(settingsStateLoc, settingsGroup.defaultState)
typeComparer = new TypeComparer(this)
typeComparer = new TypeComparer(this: @unchecked)
searchHistory = new SearchHistory(0, Map())
gadt = EmptyGADTMap
}

@sharable object NoContext extends Context {
val base: ContextBase = null
override val implicits: ContextualImplicits = new ContextualImplicits(Nil, null)(this)
override val implicits: ContextualImplicits = new ContextualImplicits(Nil, null)(this: @unchecked)
}

/** A context base defines state and associated methods that exist once per
Expand Down Expand Up @@ -673,7 +687,7 @@ object Contexts {
private[core] var phasesPlan: List[List[Phase]] = _

/** Phases by id */
private[dotc] var phases: Array[Phase] = _
final private[dotc] var phases: Array[Phase] = _

/** Phases with consecutive Transforms grouped into a single phase, Empty array if squashing is disabled */
private[core] var squashedPhases: Array[Phase] = Array.empty[Phase]
Expand Down
10 changes: 10 additions & 0 deletions compiler/src/dotty/tools/dotc/core/Definitions.scala
Original file line number Diff line number Diff line change
Expand Up @@ -806,6 +806,16 @@ class Definitions {
def SetterMetaAnnot(implicit ctx: Context): ClassSymbol = SetterMetaAnnotType.symbol.asClass
lazy val ShowAsInfixAnotType: TypeRef = ctx.requiredClassRef("scala.annotation.showAsInfix")
def ShowAsInfixAnnot(implicit ctx: Context): ClassSymbol = ShowAsInfixAnotType.symbol.asClass
lazy val IcyAnnotType: TypeRef = ctx.requiredClassRef("scala.annotation.icy")
def IcyAnnot(implicit ctx: Context): ClassSymbol = IcyAnnotType.symbol.asClass
lazy val ColdAnnotType: TypeRef = ctx.requiredClassRef("scala.annotation.cold")
def ColdAnnot(implicit ctx: Context): ClassSymbol = ColdAnnotType.symbol.asClass
lazy val WarmAnnotType: TypeRef = ctx.requiredClassRef("scala.annotation.warm")
def WarmAnnot(implicit ctx: Context): ClassSymbol = WarmAnnotType.symbol.asClass
lazy val InitAnnotType: TypeRef = ctx.requiredClassRef("scala.annotation.init")
def InitAnnot(implicit ctx: Context): ClassSymbol = InitAnnotType.symbol.asClass
lazy val CallAnnotType: TypeRef = ctx.requiredClassRef("scala.annotation.internal.Call")
def CallAnnot(implicit ctx: Context): ClassSymbol = CallAnnotType.symbol.asClass

// convenient one-parameter method types
def methOfAny(tp: Type): MethodType = MethodType(List(AnyType), tp)
Expand Down
1 change: 1 addition & 0 deletions compiler/src/dotty/tools/dotc/core/Denotations.scala
Original file line number Diff line number Diff line change
Expand Up @@ -751,6 +751,7 @@ object Denotations {
private[this] var myValidFor: Period = Nowhere

def validFor: Period = myValidFor
@scala.annotation.init
def validFor_=(p: Period): Unit = {
myValidFor = p
symbol.invalidateDenotCache()
Expand Down
9 changes: 5 additions & 4 deletions compiler/src/dotty/tools/dotc/core/NameKinds.scala
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ object NameKinds {
type ThisInfo <: Info

/** A simple info type; some subclasses of Kind define more refined versions */
@scala.annotation.cold
class Info extends NameInfo { this: ThisInfo =>
def kind: NameKind = self
def mkString(underlying: TermName): String = self.mkString(underlying, this)
Expand Down Expand Up @@ -85,7 +86,7 @@ object NameKinds {
case _ => None
}

simpleNameKinds(tag) = this
simpleNameKinds(tag) = this: @unchecked
}

/** The kind of names that get formed by adding a prefix to an underlying name */
Expand Down Expand Up @@ -151,7 +152,7 @@ object NameKinds {

def infoString: String = s"Qualified $separator"

qualifiedNameKinds(tag) = this
qualifiedNameKinds(tag) = this: @unchecked
}

/** An extractor for qualified names of an arbitrary kind */
Expand Down Expand Up @@ -188,7 +189,7 @@ object NameKinds {
else -1
}

numberedNameKinds(tag) = this
numberedNameKinds(tag) = this: @unchecked
}

/** An extractor for numbered names of arbitrary kind */
Expand Down Expand Up @@ -221,7 +222,7 @@ object NameKinds {
def fresh(prefix: TypeName)(implicit ctx: Context): TypeName =
fresh(prefix.toTermName).toTypeName

uniqueNameKinds(separator) = this
uniqueNameKinds(separator) = this: @unchecked
}

/** An extractor for unique names of arbitrary kind */
Expand Down
2 changes: 1 addition & 1 deletion compiler/src/dotty/tools/dotc/core/Names.scala
Original file line number Diff line number Diff line change
Expand Up @@ -651,7 +651,7 @@ object Names {
/** Create a type name from a string, without encoding operators */
def typeName(s: String): TypeName = typeName(s.toCharArray, 0, s.length)

table(0) = new SimpleName(-1, 0, null)
table(0) = new SimpleName(-1, 0, null): @unchecked

/** The term name represented by the empty string */
val EmptyTermName: TermName = table(0)
Expand Down
Loading