-
Notifications
You must be signed in to change notification settings - Fork 1.1k
Pure expressions are never lifted from function calls, may be copied by default getters logic without creating new symbols, leading to duplicate methods after lambdalift #2939
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
Comments
Minimization: object Test {
def foo(x: Int => Int)(y: Int = 0) = {}
def main(args: Array[String]): Unit = {
foo(x => x)()
}
} After typer we get: package <empty> {
final lazy module val Test: Test$ = new Test$()
final module class Test$() extends Object() { this: Test.type =>
def foo(x: Function1[Int, Int])(y: Int): Unit =
{
()
}
def foo$default$2(x: Function1[Int, Int]): Int = 0
def main(args: Array[String]): Unit =
{
Test.foo(
{
def $anonfun(x: Int): Int = x
closure($anonfun)
}
)(
Test.foo$default$2(
{
def $anonfun(x: Int): Int = x
closure($anonfun)
}
)
)
}
}
} Which is very fishy: The call to |
This wouldn't actually be a problem if the two methods had different symbols, but since we just copy the tree this isn't the case (https://github.com/lampepfl/dotty/blob/d916343daa86c98e739dc3b685f95410565072d9/compiler/src/dotty/tools/dotc/typer/Applications.scala#L298), and that's why lambdalift gets confused and creates two methods called |
A possible solution would be to always create fresh symbols, see https://github.com/dotty-staging/dotty/commits/fresh-symbols for how this could be done, but this isn't great for performance. Always lifting pure expressions seems like a simpler solution. We would also need to lift by-name arguments which are currently never lifted. |
Previously a method argument could be duplicated because it was passed to the method as well as to its default argument methods. This was fatal if the argument contained local definitions or was a closure. We now unconditionally lift such arguments if the method has default parameters.
Previously a method argument could be duplicated because it was passed to the method as well as to its default argument methods. This was fatal if the argument contained local definitions or was a closure. We now unconditionally lift such arguments if the method has default parameters.
Previously a method argument could be duplicated because it was passed to the method as well as to its default argument methods. This was fatal if the argument contained local definitions or was a closure. We now unconditionally lift such arguments if the method has default parameters.
Fix #2939: Avoid duplicating symbols in default arguments
Previously a method argument could be duplicated because it was passed to the method as well as to its default argument methods. This was fatal if the argument contained local definitions or was a closure. We now unconditionally lift such arguments if the method has default parameters.
Previously a method argument could be duplicated because it was passed to the method as well as to its default argument methods. This was fatal if the argument contained local definitions or was a closure. We now unconditionally lift such arguments if the method has default parameters.
For this class, Dotty does not seem to work properly:
run by dotr(0.2.0-RC1-bin-SNAPSHOT-git-54d7089):
Or compiled with SBT and then used in the repl (dottyVersion="0.3.0-bin-20170729-df4b3dd-NIGHTLY" )
The text was updated successfully, but these errors were encountered: