@@ -52,57 +52,41 @@ public class AutomaticallyRegisteredImageSingletonProcessor extends AbstractProc
5252
5353 static final String ANNOTATION_CLASS_NAME = "com.oracle.svm.core.feature.AutomaticallyRegisteredImageSingleton" ;
5454 static final String LAYERED_SINGLETON_INFO = "com.oracle.svm.core.layeredimagesingleton.LoadedLayeredImageSingletonInfo" ;
55- static final String FEATURE_SINGLETON_NAME = "com.oracle.svm.core.layeredimagesingleton.FeatureSingleton" ;
56- static final String UNSAVED_SINGLETON_NAME = "com.oracle.svm.core.layeredimagesingleton.UnsavedSingleton" ;
5755
5856 private final Set <Element > processed = new HashSet <>();
5957
6058 private void processElement (TypeElement annotatedType ) {
6159 String featureClassName = getTypeNameWithEnclosingClasses (annotatedType , "Feature" );
6260 String packageName = getPackage (annotatedType ).getQualifiedName ().toString ();
6361
64- AnnotationMirror singletonAnnotation = getAnnotation (annotatedType , getType (ANNOTATION_CLASS_NAME ));
65- AnnotationMirror platformsAnnotation = getAnnotation (annotatedType , getType ("org.graalvm.nativeimage.Platforms" ));
66-
6762 try (PrintWriter out = createSourceFile (packageName , featureClassName , processingEnv .getFiler (), annotatedType )) {
68- out .println ("// CheckStyle: stop header check" );
69- out .println ("// CheckStyle: stop line length check" );
70- out .println ("package " + packageName + ";" );
71- out .println ("" );
72- out .println ("// GENERATED CONTENT - DO NOT EDIT" );
73- out .println ("// Annotated type: " + annotatedType );
74- out .println ("// Annotation: " + ANNOTATION_CLASS_NAME );
75- out .println ("// Annotation processor: " + getClass ().getName ());
76- out .println ("" );
77- out .println ("import org.graalvm.nativeimage.ImageSingletons;" );
78- out .println ("import " + AutomaticallyRegisteredFeatureProcessor .ANNOTATION_CLASS_NAME + ";" );
79- if (platformsAnnotation != null ) {
80- out .println ("import org.graalvm.nativeimage.Platforms;" );
81- }
82- out .println ("" );
63+ AnnotationMirror singletonAnnotation = getAnnotation (annotatedType , getType (ANNOTATION_CLASS_NAME ));
64+ AnnotationMirror platformsAnnotation = getAnnotation (annotatedType , getType ("org.graalvm.nativeimage.Platforms" ));
8365
66+ String classPlatformsAnnotation = "" ;
67+ String classPlatformsImport = "" ;
8468 if (platformsAnnotation != null ) {
8569 String platforms = getAnnotationValueList (platformsAnnotation , "value" , TypeMirror .class ).stream ().map (type -> type .toString () + ".class" ).collect (Collectors .joining (", " ));
86- out .println ("@Platforms({" + platforms + "})" );
70+ classPlatformsAnnotation = System .lineSeparator () + "@Platforms({" + platforms + "})" ;
71+ classPlatformsImport = System .lineSeparator () + "import org.graalvm.nativeimage.Platforms;" ;
8772 }
88- out . println ( "@" + getSimpleName ( AutomaticallyRegisteredFeatureProcessor . ANNOTATION_CLASS_NAME ));
73+
8974 List <TypeElement > singletonSuperclasses = getSingletonSuperclasses (annotatedType );
9075 String supertypes = singletonSuperclasses .isEmpty ()
91- ? " implements " + String .join (", " , new String []{AutomaticallyRegisteredFeatureProcessor .FEATURE_INTERFACE_CLASS_NAME , FEATURE_SINGLETON_NAME , UNSAVED_SINGLETON_NAME })
92- : " extends " + getPackage (singletonSuperclasses .get (0 )).getQualifiedName ().toString () + "." + getTypeNameWithEnclosingClasses (singletonSuperclasses .get (0 ), "Feature" );
93- out .println ("public class " + featureClassName + supertypes + " {" );
94- out .println (" @Override" );
95- out .println (" public void afterRegistration(AfterRegistrationAccess access) {" );
76+ ? "implements " + AutomaticallyRegisteredFeatureProcessor .FEATURE_INTERFACE_CLASS_NAME
77+ : "extends " + getPackage (singletonSuperclasses .get (0 )).getQualifiedName ().toString () + "." + getTypeNameWithEnclosingClasses (singletonSuperclasses .get (0 ), "Feature" );
9678
79+ StringBuilder afterRegistrationBody = new StringBuilder ();
9780 List <TypeMirror > onlyWithList = getAnnotationValueList (singletonAnnotation , "onlyWith" , TypeMirror .class );
9881 if (!onlyWithList .isEmpty ()) {
9982 for (var onlyWith : onlyWithList ) {
100- out .println (" if (!new " + onlyWith + "().getAsBoolean()) {" );
101- if (!singletonSuperclasses .isEmpty ()) {
102- out .println (" super.afterRegistration(access);" );
103- }
104- out .println (" return;" );
105- out .println (" }" );
83+ String onlyWithPredicate = """
84+ if (!new %1$s().getAsBoolean()) {
85+ %2$sreturn;
86+ }
87+ """
88+ .formatted (onlyWith , singletonSuperclasses .isEmpty () ? "" : "super.afterRegistration(access);" + System .lineSeparator ());
89+ afterRegistrationBody .append (onlyWithPredicate .indent (8 ));
10690 }
10791 }
10892
@@ -112,35 +96,80 @@ private void processElement(TypeElement annotatedType) {
11296 keysFromAnnotation .addAll (getAnnotationValueList (superclassAnnotation , "value" , TypeMirror .class ));
11397 }
11498
99+ String mainBody ;
115100 if (keysFromAnnotation .isEmpty ()) {
116- String keyname = "" + annotatedType + ".class" ;
117- out .println (" if (ImageSingletons.lookup(" + LAYERED_SINGLETON_INFO + ".class).handledDuringLoading(" + keyname + ")){" );
118- out .println (" return;" );
119- out .println (" }" );
101+ String keyname = annotatedType + ".class" ;
102+ mainBody = """
103+ if (ImageSingletons.lookup(%1$s.class).handledDuringLoading(%2$s)) {
104+ return;
105+ }
106+ var singleton = new %3$s();
107+ ImageSingletons.add(%2$s, singleton);"""
108+ .formatted (LAYERED_SINGLETON_INFO , keyname , annotatedType );
120109 } else {
121- out .println (" boolean match = false;" );
122- for (var keyFromAnnotation : keysFromAnnotation ) {
123- String keyname = keyFromAnnotation .toString () + ".class" ;
124- out .println (" match = match || !ImageSingletons.lookup(" + LAYERED_SINGLETON_INFO + ".class).handledDuringLoading(" + keyname + ");" );
125- }
126- out .println (" if (!match) { return; }" );
127- }
128-
129- out .println (" var singleton = new " + annotatedType + "();" );
130110
131- if (keysFromAnnotation .isEmpty ()) {
132- String keyname = "" + annotatedType + ".class" ;
133- out .println (" ImageSingletons.add(" + keyname + ", singleton);" );
134- } else {
111+ String handledDuringLoadingTemplate = "unhandled = unhandled || !ImageSingletons.lookup(%1$s.class).handledDuringLoading(%2$s);" ;
112+ String installSingletonTemplate = """
113+ if (!ImageSingletons.lookup(%1$s.class).handledDuringLoading(%2$s)) {
114+ ImageSingletons.add(%2$s, singleton);
115+ }
116+ """ ;
117+ StringBuilder handledDuringLoadingContent = new StringBuilder ();
118+ StringBuilder installSingletonContent = new StringBuilder ();
135119 for (var keyFromAnnotation : keysFromAnnotation ) {
136- String keyname = keyFromAnnotation .toString () + ".class" ;
137- out .println (" if (!ImageSingletons.lookup(" + LAYERED_SINGLETON_INFO + ".class).handledDuringLoading(" + keyname + ")){" );
138- out .println (" ImageSingletons.add(" + keyname + ", singleton);" );
139- out .println (" }" );
120+ String keyname = keyFromAnnotation + ".class" ;
121+ handledDuringLoadingContent .append (handledDuringLoadingTemplate .formatted (LAYERED_SINGLETON_INFO , keyname )).append (System .lineSeparator ());
122+ installSingletonContent .append (installSingletonTemplate .formatted (LAYERED_SINGLETON_INFO , keyname ));
140123 }
124+ mainBody = """
125+ // checks for if the singleton was not already handled during loading
126+ boolean unhandled = false;
127+ %1$sif (!unhandled) {
128+ return;
129+ }
130+
131+ var singleton = new %2$s();
132+
133+ // adding the singleton to all keys not handled during loading
134+ %3$s"""
135+ .formatted (handledDuringLoadingContent .toString (), annotatedType , installSingletonContent .toString ());
141136 }
142- out .println (" }" );
143- out .println ("}" );
137+ afterRegistrationBody .append (mainBody .indent (8 ));
138+
139+ String javaClass = """
140+ // CheckStyle: stop header check
141+ // CheckStyle: stop line length check
142+ package %1$s;
143+
144+ // GENERATED CONTENT - DO NOT EDIT
145+ // Annotated type: %2$s
146+ // Annotation: com.oracle.svm.core.feature.AutomaticallyRegisteredImageSingleton
147+ // Annotation processor: com.oracle.svm.processor.AutomaticallyRegisteredImageSingletonProcessor
148+
149+ import org.graalvm.nativeimage.ImageSingletons;
150+
151+ import com.oracle.svm.core.feature.AutomaticallyRegisteredFeature;
152+ import com.oracle.svm.core.traits.BuiltinTraits.BuildtimeAccessOnly;
153+ import com.oracle.svm.core.traits.BuiltinTraits.NoLayeredCallbacks;
154+ import com.oracle.svm.core.traits.SingletonLayeredInstallationKind.Independent;
155+ import com.oracle.svm.core.traits.SingletonTraits;%3$s
156+
157+ @AutomaticallyRegisteredFeature%4$s
158+ @SingletonTraits(access = BuildtimeAccessOnly.class, layeredCallbacks = NoLayeredCallbacks.class, layeredInstallationKind = Independent.class)
159+ public class %5$s %6$s {
160+ @Override
161+ public void afterRegistration(AfterRegistrationAccess access) {
162+ %7$s }
163+ }"""
164+ .formatted (
165+ packageName ,
166+ annotatedType ,
167+ classPlatformsImport ,
168+ classPlatformsAnnotation ,
169+ featureClassName ,
170+ supertypes ,
171+ afterRegistrationBody );
172+ out .print (javaClass );
144173 }
145174 }
146175
0 commit comments