-
Notifications
You must be signed in to change notification settings - Fork 122
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
Unused import results in unnecessary compilation from 1.10.0-M1 onwards (regression from 1.9.6) #1461
Comments
c.c. #598 (comment) I didn't understand the exact problem either as it involved some compiler internal. I merely implemented proposed fix from @smarter to fix #598. I think the first thing we should do is to figure out what exactly is the cause for #598, and then discuss if it is indeed a compiler issue that should be fixed at compiler side instead of Zinc side. |
Seems there's a bug in sbt/zinc#1461 causing over-compilation, for now just assert the misbehavior
@smarter Would you like to join the discussion and share your thoughts on the reported issue? Since you were the one proposing the solution and you have lots of experience working with compiler internal. |
From com-lihaoyi/mill#3751 (comment):
I must say that I did not expect mutual invalidation to have this much performance impact... This basically undos the performance improvement from Stefan's consistent analysis format. @eed3si9n Should we revert for now? |
@Friendseeker It's not time-critical to revert the change for me, since I can just downgrade for the time being if necessary (com-lihaoyi/mill#3751). So unless it is time-critical for other people we can take our time to discuss what to do. I suspect that "invalidate entire cycle on change" may be necessary in some cases, so the original fix is not strictly wrong. Maybe it's even not aggressive enough since it doesn't seem to handle larger cycles with n>2. An alternative to reverting it is to just make it configurable opt-out with a flag, then people can choose their tradeoff. Whether someone prefers more occasional crashes or slower compilation for cycles would depend on the codebase and usage patterns: e.g. Mill build code currently have lots of mutual cycles and so is affected, but Mill application code does not and so is not affected by this at all. So rather than making the decision for them by reverting this we can add a config flag to let people toggle it if necessary |
Some case by case investigation is definitely needed. Currently there's 3 minimal crash reproductions documented, each with different crash stack trace (hence each likely have distinct causes)
With #535 being the most well documented. #535 has a fix planned but never released (which I guess is to let compiler traverse original type stored in tree attachment before deciding to throw).
My concern with opt-out flag is that Zinc is supposed to just work out of the box. While an opt-out flag can benefit informed Zinc users, most Scala programmers would never know about the existence of such flag. |
Since sbt or Zinc hasn't had strong opinions around source-level circular dependencies, and it seems to be causing a bunch of overcompilation that are sometimes hard to identify, it does feel like invalidating the knots might not be the right default. A good thing about crash is that it would at least prevent shipping the wrong bytecode, and the users can run |
Could we detect crashes and start over by invalidating the entire cycle automatically? That would still take time, but it will turn a bunch of manual work and confusion into an automated process that shouldnt take too much longer than pre-emptively invalidating the entire cycle anyway. And in the happy path without crashes, it would be fast |
In fact I'm guessing crashes are rare enough that invalidating the entire compilation run (not just the relevant cycle) would work too. People wouldn't mind if the compiler sometimes takes a bit longer, as long as they don't have to manually investigate and intervene to resolve an issue |
"Compiler crashed, please clean and recompile" is a common enough manual workflow outside of this specific issue that maybe we should just codify it |
The issue is that compiler throws exception whenever there's any compile error. For example in #535, the error emitted by compiler is
(c.c. #476) Which is indistinguishable from common compile error. |
Ref #1284 Fixes #1461 Fixes #1420 Also fixes com-lihaoyi/mill#3748 downstream Not sure if there's a better way to fix this? Just opening this to spark discussion The original bugs are fine, but the solution seems incorrect, and is both overly conservative (invalidating everything based on whitespace?) and not conservative enough (doesn't handle cycles with length > 2?).
project/build.properties
build.sbt
src/main/scala/build.scala
src/main/scala/subfolder/package.scala
import build.{outer => unused}
results in SBT/Zinc 1.10.0-M1 behaving correctly, only re-compiling 1 file when a newline is added to the end of either of themIt seems to me that Zinc 1.9.6 is correct and Zinc 1.10.0-M1 is wrong. In none of the cases above are any signatures or implementation code changing - I am just adding newlines to the end of the file, so even the line numbers didn't change - and thus we should not need to re-compile any downstream code. But even if we did change implementations (e.g. changing
= { 1 }
to= { 2 }
) we should not need to recompile downstream code unless signatures changeNoticed in Mill com-lihaoyi/mill#3748
Bisected the Zinc commit log and the misbehavior seems to have been introduced in 8f40c41. That code seems incorrect to me:
We are blindly including mutually-dependent files meaning two files
a <-> b
that depend on one another will be forcibly recompiled even if nothing at all changed (the test case above)We are only including directly mutually-dependent files. That means that although a 2-file cycle
a -> b -> a
is considered, a three file cyclea -> b -> c -> a
is not considered. I have verified this behavior experimentally, and can't imagine any scenarios where this distinction would be something we actually wantThe text was updated successfully, but these errors were encountered: