diff options
author | Eugene Burmako <xeno.by@gmail.com> | 2013-02-23 13:40:14 +0100 |
---|---|---|
committer | Eugene Burmako <xeno.by@gmail.com> | 2013-05-11 18:37:10 +0200 |
commit | 8168f118c9f71d63404880de89f20471043949fe (patch) | |
tree | acaa51210ad494e2ee018a68508e5c602484d88a /project | |
parent | bb73b9669a96410bc9c513d061d090f5bd3c075e (diff) | |
download | scala-8168f118c9f71d63404880de89f20471043949fe.tar.gz scala-8168f118c9f71d63404880de89f20471043949fe.tar.bz2 scala-8168f118c9f71d63404880de89f20471043949fe.zip |
[nomaster] SI-7167 implicit macros decide what is divergence
Imagine a macro writer which wants to synthesize a complex implicit
Complex[T] by making recursive calls to Complex[U] for its parts.
E.g. if we have `class Foo(val bar: Bar)` and `class Bar(val x: Int)`,
then it's quite reasonable for the macro writer to synthesize
Complex[Foo] by calling `inferImplicitValue(typeOf[Complex[Bar])`.
However if we didn't insert `info.sym.isMacro` check in `typedImplicit`,
then under some circumstances (e.g. as described in http://groups.google.com/group/scala-internals/browse_thread/thread/545462b377b0ac0a)
`dominates` might decide that `Bar` dominates `Foo` and therefore a
recursive implicit search should be prohibited.
Now when we yield control of divergent expansions to the macro writer,
what happens next? In the worst case, if the macro writer is careless,
we'll get a StackOverflowException from repeated macro calls. Otherwise,
the macro writer could check `c.openMacros` and `c.openImplicits` and
do `c.abort` when expansions are deemed to be divergent. Upon receiving
`c.abort` the typechecker will decide that the corresponding implicit
search has failed which will fail the entire stack of implicit searches,
producing a nice error message provided by the macro writer.
NOTE: the original commit from macro paradise also introduced a new
class, which encapsulates information about implicits in flight.
Unfortunately we cannot do that in 2.10.x, because of binary compatibility
concerns, therefore I'm marking this commit as [nomaster] and will be
resubmitting its full version in a separate pull request exclusively
targetting master.
Diffstat (limited to 'project')
0 files changed, 0 insertions, 0 deletions