@@ -833,64 +833,63 @@ trait Implicits { self: Typer =>
833
833
834
834
val isNot = wildProto.classSymbol == defn.NotClass
835
835
836
- /** Search a list of eligible implicit references */
837
- def searchImplicits (eligible : List [Candidate ], contextual : Boolean ): SearchResult = {
838
- val constr = ctx.typerState.constraint
839
-
840
836
// println(i"search implicits $pt / ${eligible.map(_.ref)}")
841
837
842
- /** Try to typecheck an implicit reference */
843
- def typedImplicit (cand : Candidate )(implicit ctx : Context ): SearchResult = track(" typedImplicit" ) { trace(i " typed implicit ${cand.ref}, pt = $pt, implicitsEnabled == ${ctx.mode is ImplicitsEnabled }" , implicits, show = true ) {
844
- assert(constr eq ctx.typerState.constraint)
845
- val ref = cand.ref
846
- var generated : Tree = tpd.ref(ref).withPos(pos.startPos)
847
- if (! argument.isEmpty)
848
- generated = typedUnadapted(
849
- untpd.Apply (untpd.TypedSplice (generated), untpd.TypedSplice (argument) :: Nil ),
850
- pt)
851
- val generated1 = adapt(generated, pt)
852
- lazy val shadowing =
853
- typed(untpd.Ident (cand.implicitRef.implicitName) withPos pos.toSynthetic, funProto)(
854
- nestedContext().addMode(Mode .ImplicitShadowing ).setExploreTyperState())
855
- def refSameAs (shadowing : Tree ): Boolean =
856
- ref.symbol == closureBody(shadowing).symbol || {
857
- shadowing match {
858
- case Trees .Select (qual, nme.apply) => refSameAs(qual)
859
- case Trees .Apply (fn, _) => refSameAs(fn)
860
- case Trees .TypeApply (fn, _) => refSameAs(fn)
861
- case _ => false
862
- }
838
+ /** Try to typecheck an implicit reference */
839
+ def typedImplicit (cand : Candidate , contextual : Boolean )(implicit ctx : Context ): SearchResult = track(" typedImplicit" ) { trace(i " typed implicit ${cand.ref}, pt = $pt, implicitsEnabled == ${ctx.mode is ImplicitsEnabled }" , implicits, show = true ) {
840
+ val ref = cand.ref
841
+ var generated : Tree = tpd.ref(ref).withPos(pos.startPos)
842
+ if (! argument.isEmpty)
843
+ generated = typedUnadapted(
844
+ untpd.Apply (untpd.TypedSplice (generated), untpd.TypedSplice (argument) :: Nil ),
845
+ pt)
846
+ val generated1 = adapt(generated, pt)
847
+ lazy val shadowing =
848
+ typed(untpd.Ident (cand.implicitRef.implicitName) withPos pos.toSynthetic, funProto)(
849
+ nestedContext().addMode(Mode .ImplicitShadowing ).setExploreTyperState())
850
+ def refSameAs (shadowing : Tree ): Boolean =
851
+ ref.symbol == closureBody(shadowing).symbol || {
852
+ shadowing match {
853
+ case Trees .Select (qual, nme.apply) => refSameAs(qual)
854
+ case Trees .Apply (fn, _) => refSameAs(fn)
855
+ case Trees .TypeApply (fn, _) => refSameAs(fn)
856
+ case _ => false
863
857
}
858
+ }
864
859
865
- if (ctx.reporter.hasErrors) {
866
- ctx.reporter.removeBufferedMessages
867
- SearchFailure {
868
- generated1.tpe match {
869
- case _ : SearchFailureType => generated1
870
- case _ => generated1.withType(new MismatchedImplicit (ref, pt, argument))
871
- }
860
+ if (ctx.reporter.hasErrors) {
861
+ ctx.reporter.removeBufferedMessages
862
+ SearchFailure {
863
+ generated1.tpe match {
864
+ case _ : SearchFailureType => generated1
865
+ case _ => generated1.withType(new MismatchedImplicit (ref, pt, argument))
872
866
}
873
867
}
874
- else if (contextual && ! ctx.mode.is(Mode .ImplicitShadowing ) &&
875
- ! shadowing.tpe.isError && ! refSameAs(shadowing)) {
876
- implicits.println(i " SHADOWING $ref in ${ref.termSymbol.maybeOwner} is shadowed by $shadowing in ${shadowing.symbol.maybeOwner}" )
877
- SearchFailure (generated1.withTypeUnchecked(
878
- new ShadowedImplicit (ref, methPart(shadowing).tpe, pt, argument)))
879
- }
880
- else
881
- SearchSuccess (generated1, ref, cand.level)(ctx.typerState)
882
- }}
883
-
884
- /** Try to type-check implicit reference, after checking that this is not
885
- * a diverging search
886
- */
887
- def tryImplicit (cand : Candidate ): SearchResult = {
888
- val history = ctx.searchHistory nest wildProto
889
- if (history eq ctx.searchHistory)
890
- SearchFailure (new DivergingImplicit (cand.ref, pt, argument))
891
- else
892
- typedImplicit(cand)(nestedContext().setNewTyperState().setSearchHistory(history))
893
868
}
869
+ else if (contextual && ! ctx.mode.is(Mode .ImplicitShadowing ) &&
870
+ ! shadowing.tpe.isError && ! refSameAs(shadowing)) {
871
+ implicits.println(i " SHADOWING $ref in ${ref.termSymbol.maybeOwner} is shadowed by $shadowing in ${shadowing.symbol.maybeOwner}" )
872
+ SearchFailure (generated1.withTypeUnchecked(
873
+ new ShadowedImplicit (ref, methPart(shadowing).tpe, pt, argument)))
874
+ }
875
+ else
876
+ SearchSuccess (generated1, ref, cand.level)(ctx.typerState)
877
+ }}
878
+
879
+ /** Try to type-check implicit reference, after checking that this is not
880
+ * a diverging search
881
+ */
882
+ def tryImplicit (cand : Candidate , contextual : Boolean ): SearchResult = {
883
+ val history = ctx.searchHistory nest wildProto
884
+ if (history eq ctx.searchHistory)
885
+ SearchFailure (new DivergingImplicit (cand.ref, pt, argument))
886
+ else
887
+ typedImplicit(cand, contextual)(nestedContext().setNewTyperState().setSearchHistory(history))
888
+ }
889
+
890
+ /** Search a list of eligible implicit references */
891
+ def searchImplicits (eligible : List [Candidate ], contextual : Boolean ): SearchResult = {
892
+ val constr = ctx.typerState.constraint
894
893
895
894
/** Compare previous success with reference and level to determine which one would be chosen, if
896
895
* an implicit starting with the reference was found.
@@ -963,7 +962,7 @@ trait Implicits { self: Typer =>
963
962
def rank (pending : List [Candidate ], found : SearchResult , rfailures : List [SearchFailure ]): SearchResult =
964
963
pending match {
965
964
case cand :: remaining =>
966
- negateIfNot(tryImplicit(cand)) match {
965
+ negateIfNot(tryImplicit(cand, contextual )) match {
967
966
case fail : SearchFailure =>
968
967
if (fail.isAmbiguous)
969
968
if (ctx.scala2Mode) {
@@ -1078,6 +1077,15 @@ trait Implicits { self: Typer =>
1078
1077
}
1079
1078
1080
1079
def implicitScope (tp : Type ): OfTypeImplicits = ctx.run.implicitScope(tp, ctx)
1080
+
1081
+ /** All available implicits, without ranking */
1082
+ def allImplicits : Set [TermRef ] = {
1083
+ val contextuals = ctx.implicits.eligible(wildProto).map(tryImplicit(_, contextual = true ))
1084
+ val inscope = implicitScope(wildProto).eligible.map(tryImplicit(_, contextual = false ))
1085
+ (contextuals.toSet ++ inscope).collect {
1086
+ case success : SearchSuccess => success.ref
1087
+ }
1088
+ }
1081
1089
}
1082
1090
}
1083
1091
0 commit comments