@@ -12,7 +12,7 @@ import Denotations._, Decorators._, DenotTransformers._
1212import collection .mutable
1313import util .{Property , SourceFile , NoSource }
1414import typer .ErrorReporting ._
15- import NameKinds .TempResultName
15+ import NameKinds .{ TempResultName , OuterSelectName }
1616
1717import scala .annotation .tailrec
1818import scala .io .Codec
@@ -171,6 +171,13 @@ object tpd extends Trees.Instance[Type] with TypedTreeInfo {
171171 def SyntheticValDef (name : TermName , rhs : Tree )(implicit ctx : Context ): ValDef =
172172 ValDef (ctx.newSymbol(ctx.owner, name, Synthetic , rhs.tpe.widen, coord = rhs.pos), rhs)
173173
174+ def DefDef (sym : TermSymbol , tparams : List [TypeSymbol ], vparamss : List [List [TermSymbol ]],
175+ resultType : Type , rhs : Tree )(implicit ctx : Context ): DefDef =
176+ ta.assignType(
177+ untpd.DefDef (sym.name, tparams map TypeDef , vparamss.nestedMap(ValDef (_)),
178+ TypeTree (resultType), rhs),
179+ sym)
180+
174181 def DefDef (sym : TermSymbol , rhs : Tree = EmptyTree )(implicit ctx : Context ): DefDef =
175182 ta.assignType(DefDef (sym, Function .const(rhs) _), sym)
176183
@@ -199,14 +206,7 @@ object tpd extends Trees.Instance[Type] with TypedTreeInfo {
199206 val (vparamss, rtp) = valueParamss(mtp)
200207 val targs = tparams map (_.typeRef)
201208 val argss = vparamss.nestedMap(vparam => Ident (vparam.termRef))
202- ta.assignType(
203- untpd.DefDef (
204- sym.name,
205- tparams map TypeDef ,
206- vparamss.nestedMap(ValDef (_)),
207- TypeTree (rtp),
208- rhsFn(targs)(argss)),
209- sym)
209+ DefDef (sym, tparams, vparamss, rtp, rhsFn(targs)(argss))
210210 }
211211
212212 def TypeDef (sym : TypeSymbol )(implicit ctx : Context ): TypeDef =
@@ -682,6 +682,12 @@ object tpd extends Trees.Instance[Type] with TypedTreeInfo {
682682 def select (name : Name )(implicit ctx : Context ): Select =
683683 Select (tree, name)
684684
685+ /** A select node with the given selector name such that the designated
686+ * member satisfies predicate `p`. Useful for disambiguating overloaded members.
687+ */
688+ def select (name : Name , p : Symbol => Boolean )(implicit ctx : Context ): Select =
689+ select(tree.tpe.member(name).suchThat(p).symbol)
690+
685691 /** A select node with the given type */
686692 def select (tp : NamedType )(implicit ctx : Context ): Select =
687693 untpd.Select (tree, tp.name).withType(tp)
@@ -751,9 +757,20 @@ object tpd extends Trees.Instance[Type] with TypedTreeInfo {
751757 def ensureApplied (implicit ctx : Context ): Tree =
752758 if (tree.tpe.widen.isParameterless) tree else tree.appliedToNone
753759
754- /** `tree.isInstanceOf[tp]` */
755- def isInstance (tp : Type )(implicit ctx : Context ): Tree =
756- tree.select(defn.Any_isInstanceOf ).appliedToType(tp)
760+ /** `tree == that` */
761+ def equal (that : Tree )(implicit ctx : Context ) =
762+ applyOverloaded(tree, nme.EQ , that :: Nil , Nil , defn.BooleanType )
763+
764+ /** `tree.isInstanceOf[tp]`, with special treatment of singleton types */
765+ def isInstance (tp : Type )(implicit ctx : Context ): Tree = tp match {
766+ case tp : SingletonType =>
767+ if (tp.widen.derivesFrom(defn.ObjectClass ))
768+ tree.ensureConforms(defn.ObjectType ).select(defn.Object_eq ).appliedTo(singleton(tp))
769+ else
770+ singleton(tp).equal(tree)
771+ case _ =>
772+ tree.select(defn.Any_isInstanceOf ).appliedToType(tp)
773+ }
757774
758775 /** tree.asInstanceOf[`tp`] */
759776 def asInstance (tp : Type )(implicit ctx : Context ): Tree = {
@@ -771,7 +788,7 @@ object tpd extends Trees.Instance[Type] with TypedTreeInfo {
771788 else Erasure .Boxing .adaptToType(tree, tp)
772789
773790 /** `tree ne null` (might need a cast to be type correct) */
774- def testNotNull (implicit ctx : Context ): Tree =
791+ def testNotNull (implicit ctx : Context ): Tree =
775792 tree.ensureConforms(defn.ObjectType )
776793 .select(defn.Object_ne ).appliedTo(Literal (Constant (null )))
777794
@@ -805,6 +822,13 @@ object tpd extends Trees.Instance[Type] with TypedTreeInfo {
805822 }
806823 else Assign (tree, rhs)
807824
825+ /** A synthetic select with that will be turned into an outer path by ExplicitOuter.
826+ * @param levels How many outer levels to select
827+ * @param tp The type of the destination of the outer path.
828+ */
829+ def outerSelect (levels : Int , tp : Type )(implicit ctx : Context ): Tree =
830+ untpd.Select (tree, OuterSelectName (EmptyTermName , levels)).withType(tp)
831+
808832 // --- Higher order traversal methods -------------------------------
809833
810834 /** Apply `f` to each subtree of this tree */
0 commit comments