@@ -4004,7 +4004,7 @@ object Types {
40044004 case nil => x
40054005 foldArgs(op(x, tycon), args)
40064006
4007- override def tryNormalize (using Context ): Type = tycon match {
4007+ override def tryNormalize (using Context ): Type = tycon.stripTypeVar match {
40084008 case tycon : TypeRef =>
40094009 def tryMatchAlias = tycon.info match {
40104010 case MatchAlias (alias) =>
@@ -4014,13 +4014,29 @@ object Types {
40144014 case _ =>
40154015 NoType
40164016 }
4017-
40184017 tryCompiletimeConstantFold.orElse(tryMatchAlias)
4019-
40204018 case _ =>
40214019 NoType
40224020 }
40234021
4022+ /** Does this application expand to a match type? */
4023+ def isMatchAlias (using Context ): Boolean = tycon.stripTypeVar match
4024+ case tycon : TypeRef =>
4025+ tycon.info match
4026+ case _ : MatchAlias => true
4027+ case _ => false
4028+ case _ => false
4029+
4030+ /** Is this an unreducible application to wildcard arguments?
4031+ * This is the case if tycon is higher-kinded. This means
4032+ * it is a subtype of a hk-lambda, but not a match alias.
4033+ * (normal parameterized aliases are removed in `appliedTo`).
4034+ * Applications of hgher-kinded type constructors to wildcard arguments
4035+ * are equivalent to existential types, which are not supported.
4036+ */
4037+ def isUnreducibleWild (using Context ): Boolean =
4038+ tycon.isLambdaSub && hasWildcardArg && ! isMatchAlias
4039+
40244040 def tryCompiletimeConstantFold (using Context ): Type = tycon match {
40254041 case tycon : TypeRef if defn.isCompiletimeAppliedType(tycon.symbol) =>
40264042 def constValue (tp : Type ): Option [Any ] = tp.dealias match {
@@ -5471,38 +5487,43 @@ object Types {
54715487 case Range (tyconLo, tyconHi) =>
54725488 range(derivedAppliedType(tp, tyconLo, args), derivedAppliedType(tp, tyconHi, args))
54735489 case _ =>
5474- if (args.exists(isRange))
5475- if (variance > 0 ) tp.derivedAppliedType(tycon, args.map(rangeToBounds))
5476- else {
5477- val loBuf, hiBuf = new mutable.ListBuffer [Type ]
5478- // Given `C[A1, ..., An]` where sone A's are ranges, try to find
5479- // non-range arguments L1, ..., Ln and H1, ..., Hn such that
5480- // C[L1, ..., Ln] <: C[H1, ..., Hn] by taking the right limits of
5481- // ranges that appear in as co- or contravariant arguments.
5482- // Fail for non-variant argument ranges.
5483- // If successful, the L-arguments are in loBut, the H-arguments in hiBuf.
5484- // @return operation succeeded for all arguments.
5485- def distributeArgs (args : List [Type ], tparams : List [ParamInfo ]): Boolean = args match {
5486- case Range (lo, hi) :: args1 =>
5487- val v = tparams.head.paramVarianceSign
5488- if (v == 0 ) false
5489- else {
5490- if (v > 0 ) { loBuf += lo; hiBuf += hi }
5491- else { loBuf += hi; hiBuf += lo }
5492- distributeArgs(args1, tparams.tail)
5493- }
5494- case arg :: args1 =>
5495- loBuf += arg; hiBuf += arg
5490+ if args.exists(isRange) then
5491+ if variance > 0 then
5492+ tp.derivedAppliedType(tycon, args.map(rangeToBounds)) match
5493+ case tp1 : AppliedType if tp1.isUnreducibleWild =>
5494+ // don't infer a type that would trigger an error later in
5495+ // Checling.checkAppliedType; fall through to default handling instead
5496+ case tp1 =>
5497+ return tp1
5498+ end if
5499+ val loBuf, hiBuf = new mutable.ListBuffer [Type ]
5500+ // Given `C[A1, ..., An]` where some A's are ranges, try to find
5501+ // non-range arguments L1, ..., Ln and H1, ..., Hn such that
5502+ // C[L1, ..., Ln] <: C[H1, ..., Hn] by taking the right limits of
5503+ // ranges that appear in as co- or contravariant arguments.
5504+ // Fail for non-variant argument ranges.
5505+ // If successful, the L-arguments are in loBut, the H-arguments in hiBuf.
5506+ // @return operation succeeded for all arguments.
5507+ def distributeArgs (args : List [Type ], tparams : List [ParamInfo ]): Boolean = args match {
5508+ case Range (lo, hi) :: args1 =>
5509+ val v = tparams.head.paramVarianceSign
5510+ if (v == 0 ) false
5511+ else {
5512+ if (v > 0 ) { loBuf += lo; hiBuf += hi }
5513+ else { loBuf += hi; hiBuf += lo }
54965514 distributeArgs(args1, tparams.tail)
5497- case nil =>
5498- true
5499- }
5500- if (distributeArgs(args, tp.tyconTypeParams))
5501- range(tp.derivedAppliedType(tycon, loBuf.toList),
5502- tp.derivedAppliedType(tycon, hiBuf.toList))
5503- else range(defn.NothingType , defn.AnyType )
5504- // TODO: can we give a better bound than `topType`?
5515+ }
5516+ case arg :: args1 =>
5517+ loBuf += arg; hiBuf += arg
5518+ distributeArgs(args1, tparams.tail)
5519+ case nil =>
5520+ true
55055521 }
5522+ if (distributeArgs(args, tp.tyconTypeParams))
5523+ range(tp.derivedAppliedType(tycon, loBuf.toList),
5524+ tp.derivedAppliedType(tycon, hiBuf.toList))
5525+ else range(defn.NothingType , defn.AnyType )
5526+ // TODO: can we give a better bound than `topType`?
55065527 else tp.derivedAppliedType(tycon, args)
55075528 }
55085529
0 commit comments