Skip to content

Fix #2944: propagate information from GADT bounds to normal info. #2958

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

Merged
merged 5 commits into from
Sep 21, 2017
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
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
11 changes: 10 additions & 1 deletion compiler/src/dotty/tools/dotc/transform/PostTyper.scala
Original file line number Diff line number Diff line change
Expand Up @@ -45,17 +45,26 @@ import reporting.diagnostic.messages.SuperCallsNotAllowedInline
* (11) Minimizes `call` fields of `Inline` nodes to just point to the toplevel
* class from which code was inlined.
*
* (12) Converts GADT bounds into normal type bounds
*
* The reason for making this a macro transform is that some functions (in particular
* super and protected accessors and instantiation checks) are naturally top-down and
* don't lend themselves to the bottom-up approach of a mini phase. The other two functions
* (forwarding param accessors and synthetic methods) only apply to templates and fit
* mini-phase or subfunction of a macro phase equally well. But taken by themselves
* they do not warrant their own group of miniphases before pickling.
*/
class PostTyper extends MacroTransform with IdentityDenotTransformer { thisTransformer =>
class PostTyper extends MacroTransform with SymTransformer { thisTransformer =>


import tpd._

def transformSym(ref: SymDenotation)(implicit ctx: Context): SymDenotation = {
if (ref.is(BindDefinedType) && ctx.gadt.bounds.contains(ref.symbol)) {
ref.copySymDenotation(info = ctx.gadt.bounds.apply(ref.symbol) & ref.info)
} else ref
}

/** the following two members override abstract members in Transform */
override def phaseName: String = "posttyper"

Expand Down
10 changes: 10 additions & 0 deletions tests/pos/i2944.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
trait Map2[K] {
def get(k: K): K = k
def foo: K = {
this match {
case that: Map2[b] => that.get(3.asInstanceOf[b])
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This test case passes my the check with my tests 👍

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we have a real test for this now?

//case that: Map2[c] => that.get(4.asInstanceOf[K])
Copy link
Contributor

@nicolasstucki nicolasstucki Aug 4, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This one still crashes while trying to type that.get(4.asInstanceOf[K].asInstanceOf[b @ b]).

case _ => get(5.asInstanceOf[K])
}
}
}