Hello,
On 12/2/2015 10:39 AM, Martin Buchholz wrote:
On Wed, Dec 2, 2015 at 1:32 AM, Peter Levart <peter.lev...@gmail.com> wrote:
In short, I think exceptions are a special hierarchy with special use
pattern in which clone() would not present a practical problem that
generally arises in other objects that are meant to change state
independently from their creation.
Java is supposed to be a high reliability platform and introducing new
exotic failure modes isn't something we should be doing. My work at Google
prejudices me - it seems half the work we do is trying to track down rare
bugs we can't reproduce, or happen once every cpu-year.
If you add "implements Cloneable" then people will call protected nullary
clone(). You haven't made it public, but it can (and will!) be called from
subclasses and their packages. I see you were careful to copy the
suppressedExceptions field in your static clone, but callers of the "real"
clone will produce two Throwables that share a single ArrayList, which is
not thread safe.
I'm sure there's code out there that reasonably assumes that if something
is Cloneable, then it has a public clone() method, and will try to invoke
that via reflection.
I see that if an existing subclass of Throwable implemented Cloneable,
there would be no way (short of Unsafe) for its clone method to do a proper
copy of suppressedExceptions. In the future, if Throwable were to
implement Cloneable, then more subclasses are likely to add a public
clone() method (to "support" cloning) and that will only do a proper copy
of suppressedExceptions if you do the copying in nullary Throwable.clone()
instead of in static clone.
Sadly, making Throwable Cloneable is exceedingly subtle and I think we will
regret it (as we do the design of Cloneable itself).
An anecdote about previous changes to Throwable to help justify a
cautious approach, over many years working on the JDK I've fixed over
900 bugs, some big, many small. Usually if one of my changes isn't
acceptable to push initially, it is ready to go after one or two iterations.
As part of Project Coin in JDK 7, I added suppressed exception support
to Throwable as part of the try-with-resources feature. How difficult
could it be? After the first version of the support was pushed, it
became clear that it was necessary for the suppressed exceptions to be
immutable in some circumstances, JDK-6991528, Support making
Throwable.suppressedExceptions immutable. I eventually pushed iteration
number 12 of the changes. I don't recall a bug I worked on where more
iterations were needed.
I have concerns that despite the care taken in developing this sort of
feature, there would be a complicated, subtle bug tail to work out,
especially given the larger number of subclasses of Throwable.
-Joe