Desugaring of anonymous classes
Alex Buckley
alex.buckley at oracle.com
Mon Aug 5 17:00:12 PDT 2013
Mike, Srikanth,
Returning to this topic, there are two scenarios where I would like your
comments:
1. Type annotation in 'new' expression for anonymous class
Consider this code:
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE_USE)
@interface X {}
class C { void m() { new @X Foo() {}; } }
The @X annotation is stored as a target_type=CLASS_EXTENDS structure in
the RuntimeVisibleTypeAnnotations attribute of Foo$1.class. That's fine.
The @X annotation is not stored as a target_type=NEW structure in the
RuntimeVisibleTypeAnnotations attribute of m's method_info in C.class.
That's an oversight by javac, especially since the first mail in this
thread said javac copied type annotations "to the class declaration and
to its instantiation (new expression)".
2. Declaration annotation for anonymous class in 'new' expression
Take the code above and change the annotation type's target to be TYPE:
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE)
@interface X {}
class C { void m() { new @X Foo() {}; } }
The @X annotation is stored in the RuntimeVisibleAnnotations structure
of Foo$1.class. This is a neat trick, since anonymous class declarations
could not be annotated in SE 7, but it is irregular because annotations
on declarations traditionally appear as modifiers. If a 'new' expression
is to provide a declaration context (for TYPE annotations) as well as a
type context (for TYPE_USE annotations), then the spec needs to spell it
out.
What's more, annotations on anonymous class declarations could have
implications for core reflection and other language features. It appears
that "new @X @X Foo() {};" works at compile-time, but I have not tried
reflecting over Foo$1.class's RuntimeVisibleAnnotations attribute.
Alex
On 4/1/2013 12:59 PM, Alex Buckley wrote:
> On 3/31/2013 11:39 AM, Michael Ernst wrote:
>> In January, I removed the text from the specification that was
>> compiler-specific. This text was among the removed text:
>>
>> As another example, an anonymous class desugars into a class
>> declaration
>> and instantiation. A programmer may write both type and declaration
>> annotations on an anonymous class in Java source code. In the
>> classfile,
>> the type annotations are copied to the class declaration and to its
>> instantiation (new expression). The declaration annotations are
>> copied
>> only to the class declaration.
>>
>> Do you consider this possibly implementation-specific, and therefore it
>> does not belong in the specification. Or, will every compiler follow
>> this
>> implementation strategy so it is worth re-instating as useful guidance?
>
> It would be better to start with the concept of a class instance
> creation expression (CICE) since it lets the locations be more precise.
>
> A CICE may create an instance of an anonymous class, in which case the
> declaration of the anonymous class is provided inline. This declaration
> is required by JLS 13.1 to compile to a form with a binary name; you can
> take this to mean a standalone class file is emitted.
>
> A CICE may have i) type annotations in the 'new ... {' term outside the
> anonymous class declaration, and ii) type annotations and declaration
> annotations inside the anonymous class declaration. It would be
> appropriate to specify:
>
> - The (i) annotations (type only) are stored for the CICE in its
> enclosing class file _and_ stored for the superclass of the anonymous
> class declaration in its emitted class file.
>
> - The (ii) annotations (type and decl) are stored for the appropriate
> type uses and declarations in the class file emitted for the anonymous
> class declaration.
>
> Alex
More information about the type-annotations-spec-experts
mailing list