@@ -2006,9 +2006,48 @@ class Typer extends Namer with TypeAssigner with Applications with Implicits wit
20062006 // prioritize method parameter types as parameter types of the eta-expanded closure
20072007 0
20082008 else defn.functionArity(ptNorm)
2009- else if (pt eq AnyFunctionProto ) wtp.paramInfos.length
2010- else - 1
2011- if (arity >= 0 && ! tree.symbol.isConstructor)
2009+ else {
2010+ val nparams = wtp.paramInfos.length
2011+ if (nparams > 0 || pt.eq(AnyFunctionProto )) nparams
2012+ else - 1 // no eta expansion in this case
2013+ }
2014+
2015+ /** A synthetic apply should be eta-expanded if it is the apply of an implicit function
2016+ * class, and the expected type is a function type. This rule is needed so we can pass
2017+ * an implicit function to a regular function type. So the following is OK
2018+ *
2019+ * val f: implicit A => B = ???
2020+ * val g: A => B = f
2021+ *
2022+ * and the last line expands to
2023+ *
2024+ * val g: A => B = (x$0: A) => f.apply(x$0)
2025+ *
2026+ * One could be tempted not to eta expand the rhs, but that would violate the invariant
2027+ * that expressions of implicit function types are always implicit closures, which is
2028+ * exploited by ShortcutImplicits.
2029+ *
2030+ * On the other hand, the following would give an error if there is no implicit
2031+ * instance of A available.
2032+ *
2033+ * val x: AnyRef = f
2034+ *
2035+ * That's intentional, we want to fail here, otherwise some unsuccesful implicit searches
2036+ * would go undetected.
2037+ *
2038+ * Examples for these cases are found in run/implicitFuns.scala and neg/i2006.scala.
2039+ */
2040+ def isExpandableApply =
2041+ defn.isImplicitFunctionClass(tree.symbol.maybeOwner) && defn.isFunctionType(ptNorm)
2042+
2043+ // Reasons NOT to eta expand:
2044+ // - we reference a constructor
2045+ // - we are in a patterm
2046+ // - the current tree is a synthetic apply which is not expandable (eta-expasion would simply undo that)
2047+ if (arity >= 0 &&
2048+ ! tree.symbol.isConstructor &&
2049+ ! ctx.mode.is(Mode .Pattern ) &&
2050+ ! (isSyntheticApply(tree) && ! isExpandableApply))
20122051 typed(etaExpand(tree, wtp, arity), pt)
20132052 else if (wtp.paramInfos.isEmpty)
20142053 adaptInterpolated(tpd.Apply (tree, Nil ), pt, EmptyTree )
0 commit comments