27
27
import java .lang .invoke .CallSite ;
28
28
import java .lang .invoke .MethodHandle ;
29
29
import java .lang .invoke .MethodType ;
30
- import java .lang .reflect . Array ;
30
+ import java .lang .invoke . VarHandle ;
31
31
import java .lang .reflect .Field ;
32
32
import java .lang .reflect .InvocationTargetException ;
33
33
import java .lang .reflect .Member ;
34
34
import java .lang .reflect .Method ;
35
- import java .util .Iterator ;
36
35
import java .util .Optional ;
37
36
import java .util .concurrent .ConcurrentHashMap ;
38
37
import java .util .function .Supplier ;
@@ -108,20 +107,20 @@ public class MethodHandleFeature implements InternalFeature {
108
107
109
108
@ Override
110
109
public void duringSetup (DuringSetupAccess access ) {
111
- Class <?> memberNameClass = access . findClassByName ("java.lang.invoke.MemberName" );
110
+ Class <?> memberNameClass = ReflectionUtil . lookupClass ("java.lang.invoke.MemberName" );
112
111
memberNameIsMethod = ReflectionUtil .lookupMethod (memberNameClass , "isMethod" );
113
112
memberNameIsConstructor = ReflectionUtil .lookupMethod (memberNameClass , "isConstructor" );
114
113
memberNameIsField = ReflectionUtil .lookupMethod (memberNameClass , "isField" );
115
114
memberNameGetMethodType = ReflectionUtil .lookupMethod (memberNameClass , "getMethodType" );
116
115
117
- Class <?> arrayAccessorClass = access . findClassByName ("java.lang.invoke.MethodHandleImpl$ArrayAccessor" );
116
+ Class <?> arrayAccessorClass = ReflectionUtil . lookupClass ("java.lang.invoke.MethodHandleImpl$ArrayAccessor" );
118
117
typedAccessors = ReflectionUtil .lookupField (arrayAccessorClass , "TYPED_ACCESSORS" );
119
- Class <?> methodHandleImplClass = access . findClassByName ("java.lang.invoke.MethodHandleImpl$Makers" );
120
- typedCollectors = ReflectionUtil .lookupField (methodHandleImplClass , "TYPED_COLLECTORS" );
118
+ Class <?> makersClass = ReflectionUtil . lookupClass ("java.lang.invoke.MethodHandleImpl$Makers" );
119
+ typedCollectors = ReflectionUtil .lookupField (makersClass , "TYPED_COLLECTORS" );
121
120
122
121
if (JavaVersionUtil .JAVA_SPEC >= 22 ) {
123
122
try {
124
- Class <?> referencedKeySetClass = access . findClassByName ("jdk.internal.util.ReferencedKeySet" );
123
+ Class <?> referencedKeySetClass = ReflectionUtil . lookupClass ("jdk.internal.util.ReferencedKeySet" );
125
124
Method create = ReflectionUtil .lookupMethod (referencedKeySetClass , "create" , boolean .class , boolean .class , Supplier .class );
126
125
// The following call must match the static initializer of MethodType#internTable.
127
126
runtimeMethodTypeInternTable = create .invoke (null ,
@@ -131,7 +130,7 @@ public void duringSetup(DuringSetupAccess access) {
131
130
throw VMError .shouldNotReachHere (e );
132
131
}
133
132
} else {
134
- Class <?> concurrentWeakInternSetClass = access . findClassByName ("java.lang.invoke.MethodType$ConcurrentWeakInternSet" );
133
+ Class <?> concurrentWeakInternSetClass = ReflectionUtil . lookupClass ("java.lang.invoke.MethodType$ConcurrentWeakInternSet" );
135
134
runtimeMethodTypeInternTable = ReflectionUtil .newInstance (concurrentWeakInternSetClass );
136
135
referencedKeySetAdd = ReflectionUtil .lookupMethod (concurrentWeakInternSetClass , "add" , Object .class );
137
136
}
@@ -148,45 +147,22 @@ public void duringSetup(DuringSetupAccess access) {
148
147
public void beforeAnalysis (BeforeAnalysisAccess a ) {
149
148
var access = (BeforeAnalysisAccessImpl ) a ;
150
149
151
- /* java.lang.invoke functions called through reflection */
152
- Class <?> mhImplClazz = access .findClassByName ("java.lang.invoke.MethodHandleImpl" );
153
-
154
- access .registerReachabilityHandler (MethodHandleFeature ::registerMHImplFunctionsForReflection ,
155
- ReflectionUtil .lookupMethod (mhImplClazz , "getFunction" , byte .class ));
156
-
157
- access .registerReachabilityHandler (MethodHandleFeature ::registerMHImplConstantHandlesForReflection ,
158
- ReflectionUtil .lookupMethod (mhImplClazz , "makeConstantHandle" , int .class ));
159
-
160
- access .registerReachabilityHandler (MethodHandleFeature ::registerMHImplCountingWrapperFunctionsForReflection ,
161
- access .findClassByName ("java.lang.invoke.MethodHandleImpl$CountingWrapper" ));
162
-
163
- access .registerReachabilityHandler (MethodHandleFeature ::registerInvokersFunctionsForReflection ,
164
- ReflectionUtil .lookupMethod (access .findClassByName ("java.lang.invoke.Invokers" ), "getFunction" , byte .class ));
165
-
150
+ eagerlyInitializeMHImplFunctions ();
151
+ eagerlyInitializeMHImplConstantHandles ();
152
+ eagerlyInitializeInvokersFunctions ();
166
153
eagerlyInitializeValueConversionsCaches ();
154
+ eagerlyInitializeCallSite ();
167
155
168
- access .registerClassInitializerReachabilityHandler (MethodHandleFeature ::registerDelegatingMHFunctionsForReflection ,
169
- access .findClassByName ("java.lang.invoke.DelegatingMethodHandle" ));
170
-
171
- access .registerReachabilityHandler (MethodHandleFeature ::registerCallSiteGetTargetForReflection ,
172
- ReflectionUtil .lookupMethod (CallSite .class , "getTargetHandle" ));
173
-
174
- access .registerReachabilityHandler (MethodHandleFeature ::registerUninitializedCallSiteForReflection ,
175
- ReflectionUtil .lookupMethod (CallSite .class , "uninitializedCallSiteHandle" ));
176
-
177
- access .registerSubtypeReachabilityHandler (MethodHandleFeature ::registerVarHandleMethodsForReflection ,
178
- access .findClassByName ("java.lang.invoke.VarHandle" ));
179
-
180
- access .registerSubtypeReachabilityHandler (MethodHandleFeature ::scanBoundMethodHandle ,
181
- access .findClassByName ("java.lang.invoke.BoundMethodHandle" ));
156
+ access .registerSubtypeReachabilityHandler (MethodHandleFeature ::registerVarHandleMethodsForReflection , VarHandle .class );
157
+ access .registerSubtypeReachabilityHandler (MethodHandleFeature ::scanBoundMethodHandle , ReflectionUtil .lookupClass ("java.lang.invoke.BoundMethodHandle" ));
182
158
183
159
AnalysisMetaAccess metaAccess = access .getMetaAccess ();
184
160
ImageHeapScanner heapScanner = access .getUniverse ().getHeapScanner ();
185
161
186
162
access .registerFieldValueTransformer (
187
- ReflectionUtil .lookupField (ReflectionUtil .lookupClass (false , "java.lang.invoke.ClassSpecializer" ), "cache" ),
163
+ ReflectionUtil .lookupField (ReflectionUtil .lookupClass ("java.lang.invoke.ClassSpecializer" ), "cache" ),
188
164
new FieldValueTransformerWithAvailability () {
189
- private static final Class <?> speciesDataClass = ReflectionUtil .lookupClass (false , "java.lang.invoke.ClassSpecializer$SpeciesData" );
165
+ private static final Class <?> SPECIES_DATA_CLASS = ReflectionUtil .lookupClass ("java.lang.invoke.ClassSpecializer$SpeciesData" );
190
166
191
167
/*
192
168
* The value of the ClassSpecializer.cache is not seen by the analysis
@@ -215,16 +191,16 @@ public Object transform(Object receiver, Object originalValue) {
215
191
}
216
192
217
193
private boolean isSpeciesTypeInstantiated (Object speciesData ) {
218
- Class <?> speciesClass = ReflectionUtil .readField (speciesDataClass , "speciesCode" , speciesData );
194
+ Class <?> speciesClass = ReflectionUtil .readField (SPECIES_DATA_CLASS , "speciesCode" , speciesData );
219
195
Optional <AnalysisType > analysisType = metaAccess .optionalLookupJavaType (speciesClass );
220
196
return analysisType .isPresent () && analysisType .get ().isInstantiated ();
221
197
}
222
198
});
223
199
access .registerFieldValueTransformer (
224
- ReflectionUtil .lookupField (ReflectionUtil .lookupClass (false , "java.lang.invoke.DirectMethodHandle" ), "ACCESSOR_FORMS" ),
200
+ ReflectionUtil .lookupField (ReflectionUtil .lookupClass ("java.lang.invoke.DirectMethodHandle" ), "ACCESSOR_FORMS" ),
225
201
NewEmptyArrayFieldValueTransformer .INSTANCE );
226
202
access .registerFieldValueTransformer (
227
- ReflectionUtil .lookupField (ReflectionUtil .lookupClass (false , "java.lang.invoke.MethodType" ), "internTable" ),
203
+ ReflectionUtil .lookupField (ReflectionUtil .lookupClass ("java.lang.invoke.MethodType" ), "internTable" ),
228
204
(receiver , originalValue ) -> runtimeMethodTypeInternTable );
229
205
230
206
/*
@@ -236,7 +212,7 @@ private boolean isSpeciesTypeInstantiated(Object speciesData) {
236
212
* be made reachable after analysis.
237
213
*/
238
214
access .registerFieldValueTransformer (
239
- ReflectionUtil .lookupField (ReflectionUtil .lookupClass (false , "java.lang.invoke.ClassSpecializer$SpeciesData" ), "transformHelpers" ),
215
+ ReflectionUtil .lookupField (ReflectionUtil .lookupClass ("java.lang.invoke.ClassSpecializer$SpeciesData" ), "transformHelpers" ),
240
216
new FieldValueTransformerWithAvailability () {
241
217
@ Override
242
218
public boolean isAvailable () {
@@ -267,8 +243,8 @@ public Object transform(Object receiver, Object originalValue) {
267
243
* method Feature.beforeCompilation()), thereby registering new elements into the image heap
268
244
* (elements that were not tracked in the analysis).
269
245
*/
270
- Class <?> lambdaFormClass = ReflectionUtil .lookupClass (false , "java.lang.invoke.LambdaForm" );
271
- Class <?> basicTypeClass = ReflectionUtil .lookupClass (false , "java.lang.invoke.LambdaForm$BasicType" );
246
+ Class <?> lambdaFormClass = ReflectionUtil .lookupClass ("java.lang.invoke.LambdaForm" );
247
+ Class <?> basicTypeClass = ReflectionUtil .lookupClass ("java.lang.invoke.LambdaForm$BasicType" );
272
248
Method createFormsForMethod = ReflectionUtil .lookupMethod (lambdaFormClass , "createFormsFor" , basicTypeClass );
273
249
try {
274
250
for (Object type : (Object []) ReflectionUtil .readStaticField (basicTypeClass , "ALL_TYPES" )) {
@@ -279,43 +255,31 @@ public Object transform(Object receiver, Object originalValue) {
279
255
}
280
256
}
281
257
282
- private static void registerMHImplFunctionsForReflection (DuringAnalysisAccess access ) {
283
- Class <?> mhImplClazz = access .findClassByName ("java.lang.invoke.MethodHandleImpl" );
284
- RuntimeReflection .register (ReflectionUtil .lookupMethod (mhImplClazz , "checkSpreadArgument" , Object .class , int .class ));
285
- RuntimeReflection .register (ReflectionUtil .lookupMethod (mhImplClazz , "guardWithCatch" , MethodHandle .class , Class .class , MethodHandle .class , Object [].class ));
286
- RuntimeReflection .register (ReflectionUtil .lookupMethod (mhImplClazz , "tryFinally" , MethodHandle .class , MethodHandle .class , Object [].class ));
287
- RuntimeReflection .register (ReflectionUtil .lookupMethod (mhImplClazz , "loop" , access .findClassByName ("[Ljava.lang.invoke.LambdaForm$BasicType;" ),
288
- access .findClassByName ("java.lang.invoke.MethodHandleImpl$LoopClauses" ), Object [].class ));
289
- RuntimeReflection .register (ReflectionUtil .lookupMethod (mhImplClazz , "throwException" , Throwable .class ));
290
- RuntimeReflection .register (ReflectionUtil .lookupMethod (mhImplClazz , "profileBoolean" , boolean .class , int [].class ));
291
- }
292
-
293
- private static void registerMHImplConstantHandlesForReflection (DuringAnalysisAccess access ) {
294
- Class <?> mhImplClazz = access .findClassByName ("java.lang.invoke.MethodHandleImpl" );
295
- RuntimeReflection .register (ReflectionUtil .lookupMethod (mhImplClazz , "selectAlternative" , boolean .class , MethodHandle .class , MethodHandle .class ));
296
- RuntimeReflection .register (ReflectionUtil .lookupMethod (mhImplClazz , "countedLoopPredicate" , int .class , int .class ));
297
- RuntimeReflection .register (ReflectionUtil .lookupMethod (mhImplClazz , "countedLoopStep" , int .class , int .class ));
298
- RuntimeReflection .register (ReflectionUtil .lookupMethod (mhImplClazz , "initIterator" , Iterable .class ));
299
- RuntimeReflection .register (ReflectionUtil .lookupMethod (mhImplClazz , "iteratePredicate" , Iterator .class ));
300
- RuntimeReflection .register (ReflectionUtil .lookupMethod (mhImplClazz , "iterateNext" , Iterator .class ));
301
- RuntimeReflection .register (ReflectionUtil .lookupMethod (Array .class , "newInstance" , Class .class , int .class ));
258
+ private static void eagerlyInitializeMHImplFunctions () {
259
+ var methodHandleImplClass = ReflectionUtil .lookupClass ("java.lang.invoke.MethodHandleImpl" );
260
+ int count = ((Object []) ReflectionUtil .readStaticField (methodHandleImplClass , "NFS" )).length ;
261
+ var getFunctionMethod = ReflectionUtil .lookupMethod (methodHandleImplClass , "getFunction" , byte .class );
262
+ for (int i = 0 ; i < count ; i ++) {
263
+ ReflectionUtil .invokeMethod (getFunctionMethod , null , (byte ) i );
264
+ }
302
265
}
303
266
304
- private static void registerMHImplCountingWrapperFunctionsForReflection (DuringAnalysisAccess access ) {
305
- RuntimeReflection .register (ReflectionUtil .lookupMethod (access .findClassByName ("java.lang.invoke.MethodHandleImpl$CountingWrapper" ), "maybeStopCounting" , Object .class ));
267
+ private static void eagerlyInitializeMHImplConstantHandles () {
268
+ var methodHandleImplClass = ReflectionUtil .lookupClass ("java.lang.invoke.MethodHandleImpl" );
269
+ int count = ((Object []) ReflectionUtil .readStaticField (methodHandleImplClass , "HANDLES" )).length ;
270
+ var getConstantHandleMethod = ReflectionUtil .lookupMethod (methodHandleImplClass , "getConstantHandle" , int .class );
271
+ for (int i = 0 ; i < count ; i ++) {
272
+ ReflectionUtil .invokeMethod (getConstantHandleMethod , null , i );
273
+ }
306
274
}
307
275
308
- private static void registerInvokersFunctionsForReflection (DuringAnalysisAccess access ) {
309
- Class <?> invokersClazz = access .findClassByName ("java.lang.invoke.Invokers" );
310
- RuntimeReflection .register (ReflectionUtil .lookupMethod (invokersClazz , "checkExactType" , MethodHandle .class , MethodType .class ));
311
- RuntimeReflection .register (ReflectionUtil .lookupMethod (invokersClazz , "checkGenericType" , MethodHandle .class , MethodType .class ));
312
- RuntimeReflection .register (ReflectionUtil .lookupMethod (invokersClazz , "getCallSiteTarget" , CallSite .class ));
313
- RuntimeReflection .register (ReflectionUtil .lookupMethod (invokersClazz , "checkCustomized" , MethodHandle .class ));
314
- RuntimeReflection .register (ReflectionUtil .lookupMethod (invokersClazz , "checkVarHandleGenericType" , access .findClassByName ("java.lang.invoke.VarHandle" ),
315
- access .findClassByName ("java.lang.invoke.VarHandle$AccessDescriptor" )));
316
- RuntimeReflection .register (ReflectionUtil .lookupMethod (invokersClazz , "checkVarHandleExactType" , access .findClassByName ("java.lang.invoke.VarHandle" ),
317
- access .findClassByName ("java.lang.invoke.VarHandle$AccessDescriptor" )));
318
- RuntimeReflection .register (ReflectionUtil .lookupMethod (invokersClazz , "directVarHandleTarget" , access .findClassByName ("java.lang.invoke.VarHandle" )));
276
+ private static void eagerlyInitializeInvokersFunctions () {
277
+ var invokerksClass = ReflectionUtil .lookupClass ("java.lang.invoke.Invokers" );
278
+ int count = ((Object []) ReflectionUtil .readStaticField (invokerksClass , "NFS" )).length ;
279
+ var getFunctionMethod = ReflectionUtil .lookupMethod (invokerksClass , "getFunction" , byte .class );
280
+ for (int i = 0 ; i < count ; i ++) {
281
+ ReflectionUtil .invokeMethod (getFunctionMethod , null , (byte ) i );
282
+ }
319
283
}
320
284
321
285
/**
@@ -344,21 +308,13 @@ private static void eagerlyInitializeValueConversionsCaches() {
344
308
}
345
309
}
346
310
347
- private static void registerDelegatingMHFunctionsForReflection (DuringAnalysisAccess access ) {
348
- Class <?> delegatingMHClazz = access .findClassByName ("java.lang.invoke.DelegatingMethodHandle" );
349
- RuntimeReflection .register (ReflectionUtil .lookupMethod (delegatingMHClazz , "getTarget" ));
350
- }
351
-
352
- private static void registerCallSiteGetTargetForReflection (DuringAnalysisAccess access ) {
353
- RuntimeReflection .register (ReflectionUtil .lookupMethod (CallSite .class , "getTarget" ));
354
- }
355
-
356
- private static void registerUninitializedCallSiteForReflection (DuringAnalysisAccess access ) {
357
- RuntimeReflection .register (ReflectionUtil .lookupMethod (CallSite .class , "uninitializedCallSite" , Object [].class ));
311
+ private static void eagerlyInitializeCallSite () {
312
+ ReflectionUtil .invokeMethod (ReflectionUtil .lookupMethod (CallSite .class , "getTargetHandle" ), null );
313
+ ReflectionUtil .invokeMethod (ReflectionUtil .lookupMethod (CallSite .class , "uninitializedCallSiteHandle" ), null );
358
314
}
359
315
360
316
private static void registerVarHandleMethodsForReflection (FeatureAccess access , Class <?> subtype ) {
361
- if (subtype .getPackage ().getName ().equals ("java.lang.invoke" ) && subtype != access . findClassByName ( "java.lang.invoke. VarHandle" ) ) {
317
+ if (subtype .getPackage ().getName ().equals ("java.lang.invoke" ) && subtype != VarHandle . class ) {
362
318
RuntimeReflection .register (subtype .getDeclaredMethods ());
363
319
}
364
320
}
0 commit comments