RFC: fix PR 28892

David Daney ddaney@avtrex.com
Thu Aug 31 18:58:00 GMT 2006


Andrew Haley wrote:
> David Daney writes:
>  > Tom Tromey wrote:
>  > >>>>>>"Andrew" == Andrew Haley <aph@redhat.com> writes:
>  > > 
>  > > 
>  > > Andrew> I'd have made it WONTFIX.  Sadly, however, there seems to be no rule
>  > > Andrew> in the specification that forbids final fields being rewritten in
>  > > Andrew> methods other than clinit.
>  > > 
>  > > In this case I don't think the fields are being rewritten -- they are
>  > > simply being initialized by a different function.
>  > > 
>  > > Andrew> This makes some optimizations harder.  I think we need a flag to tell
>  > > Andrew> gcj that what we are compiling may not be Java code.  Then we can do
>  > > Andrew> better optimizations when we know that it is.
>  > > 
>  > > Unfortunately I think final fields may be changed via reflection.
>  > > 
>  > 
>  > Is this behavior specified anywhere?
>  > 
>  > I have not carefully read JLS 3, but IIRC in the good old days, it was 
>  > kind of unspecified behavior.
> 
> Well, if you can find that in JLS 2 you're better at reading specs
> than me!  There are some restrictions on putfield, but I can't see
> that one.

Well I think I found the relevant documentation.  The JLS defers to the 
API documentation for things in the standard library.

Look in: http://java.sun.com/j2se/1.5.0/docs/api/

The documentation for java.lang.reflect.Field.set(Object,Object) says:

"If the underlying field is final, the method throws an 
IllegalAccessException unless setAccessible(true) has succeeded for this 
field and this field is non-static. Setting a final field in this way is 
meaningful only during deserialization or reconstruction of instances of 
classes with blank final fields, before they are made available for 
access by other parts of a program. Use in any other context may have 
unpredictable effects, including cases in which other parts of a program 
continue to use the original value of this field."

Earlier versions of the JDK specified that an IllegalAccessException was 
thrown unconditionally, but I think behaved in the manner documented for 
  JDK 1.5.

If you try to modify a final field directly (after it has been set) the 
verifier must reject the code.  So the only option would be to use 
reflection, for which it is only supposed to work in a very narrow set 
of circumstances.

David Daney.





More information about the Gcc-patches mailing list