16
16
import java .util .ArrayList ;
17
17
import java .util .Arrays ;
18
18
import java .util .Collections ;
19
- import java .util .Iterator ;
20
19
import java .util .List ;
21
20
import java .util .Map ;
22
21
import java .util .concurrent .Callable ;
@@ -282,13 +281,13 @@ public ReflectionOptimizer getReflectionOptimizer(
282
281
}
283
282
}
284
283
285
- private static class ForeignPackageClassInfo {
284
+ private static class BridgeMembersClassInfo {
286
285
final Class <?> clazz ;
287
286
final List <String > propertyNames = new ArrayList <>();
288
287
final List <Member > getters = new ArrayList <>();
289
288
final List <Member > setters = new ArrayList <>();
290
289
291
- public ForeignPackageClassInfo (Class <?> clazz ) {
290
+ public BridgeMembersClassInfo (Class <?> clazz ) {
292
291
this .clazz = clazz ;
293
292
}
294
293
}
@@ -297,93 +296,75 @@ private Class<?> determineAccessOptimizerSuperClass(Class<?> clazz, String[] pro
297
296
if ( clazz .isInterface () ) {
298
297
return Object .class ;
299
298
}
300
- // generate access optimizer super classes for foreign package super classes that declare fields
299
+ // generate access optimizer super classes for super classes that declare members requiring bridge methods
301
300
// each should declare protected static methods get_FIELDNAME(OWNER)/set_FIELDNAME(OWNER, TYPE)
302
301
// which should be called then from within GetPropertyValues/SetPropertyValues
303
302
// Since these super classes will be in the correct package, the package-private entity field access is fine
304
- final List <ForeignPackageClassInfo > foreignPackageClassInfos = createForeignPackageClassInfos ( clazz );
305
- for ( Iterator <ForeignPackageClassInfo > iterator = foreignPackageClassInfos .iterator (); iterator .hasNext (); ) {
306
- final ForeignPackageClassInfo foreignPackageClassInfo = iterator .next ();
307
- for ( int i = 0 ; i < getters .length ; i ++ ) {
308
- final Member getter = getters [i ];
309
- final Member setter = setters [i ];
310
- boolean found = false ;
311
- if ( getter .getDeclaringClass () == foreignPackageClassInfo .clazz && !Modifier .isPublic ( getter .getModifiers () ) ) {
312
- foreignPackageClassInfo .getters .add ( getter );
313
- found = true ;
314
- }
315
- if ( setter .getDeclaringClass () == foreignPackageClassInfo .clazz && !Modifier .isPublic ( setter .getModifiers () ) ) {
316
- foreignPackageClassInfo .setters .add ( setter );
317
- found = true ;
318
- }
319
- if ( found ) {
320
- foreignPackageClassInfo .propertyNames .add ( propertyNames [i ] );
321
- }
322
- }
323
- if ( foreignPackageClassInfo .getters .isEmpty () && foreignPackageClassInfo .setters .isEmpty () ) {
324
- iterator .remove ();
325
- }
326
- }
303
+ final List <BridgeMembersClassInfo > bridgeMembersClassInfos = createBridgeMembersClassInfos ( clazz , getters , setters , propertyNames );
327
304
328
305
Class <?> superClass = Object .class ;
329
- for ( int i = foreignPackageClassInfos .size () - 1 ; i >= 0 ; i -- ) {
330
- final ForeignPackageClassInfo foreignPackageClassInfo = foreignPackageClassInfos .get ( i );
306
+ for ( int i = bridgeMembersClassInfos .size () - 1 ; i >= 0 ; i -- ) {
307
+ final BridgeMembersClassInfo bridgeMembersClassInfo = bridgeMembersClassInfos .get ( i );
331
308
final Class <?> newSuperClass = superClass ;
332
309
333
- final String className = foreignPackageClassInfo .clazz .getName () + "$" + OPTIMIZER_PROXY_BRIDGE_NAMING_SUFFIX + encodeName ( foreignPackageClassInfo .propertyNames , foreignPackageClassInfo .getters , foreignPackageClassInfo .setters );
310
+ final String className = bridgeMembersClassInfo .clazz .getName () + "$" + OPTIMIZER_PROXY_BRIDGE_NAMING_SUFFIX + encodeName ( bridgeMembersClassInfo .propertyNames , bridgeMembersClassInfo .getters , bridgeMembersClassInfo .setters );
334
311
superClass = byteBuddyState .load (
335
- foreignPackageClassInfo .clazz ,
312
+ bridgeMembersClassInfo .clazz ,
336
313
className ,
337
314
(byteBuddy , namingStrategy ) -> {
338
315
DynamicType .Builder <?> builder = byteBuddy .with ( namingStrategy ).subclass ( newSuperClass );
339
- for ( Member getter : foreignPackageClassInfo .getters ) {
340
- final Class <?> getterType ;
341
- if ( getter instanceof Field ) {
342
- getterType = ( (Field ) getter ).getType ();
343
- }
344
- else {
345
- getterType = ( (Method ) getter ).getReturnType ();
316
+ for ( Member getter : bridgeMembersClassInfo .getters ) {
317
+ if ( !Modifier .isPublic ( getter .getModifiers () ) ) {
318
+ final Class <?> getterType ;
319
+ if ( getter instanceof Field ) {
320
+ getterType = ( (Field ) getter ).getType ();
321
+ }
322
+ else {
323
+ getterType = ( (Method ) getter ).getReturnType ();
324
+ }
325
+
326
+ builder = builder .defineMethod (
327
+ "get_" + getter .getName (),
328
+ TypeDescription .Generic .OfNonGenericType .ForLoadedType .of (
329
+ getterType
330
+ ),
331
+ Opcodes .ACC_PROTECTED | Opcodes .ACC_STATIC
332
+ )
333
+ .withParameter ( bridgeMembersClassInfo .clazz )
334
+ .intercept (
335
+ new Implementation .Simple (
336
+ new GetFieldOnArgument (
337
+ getter
338
+ )
339
+ )
340
+ );
346
341
}
347
-
348
- builder = builder .defineMethod (
349
- "get_" + getter .getName (),
350
- TypeDescription .Generic .OfNonGenericType .ForLoadedType .of (
351
- getterType
352
- ),
353
- Opcodes .ACC_PROTECTED | Opcodes .ACC_STATIC
354
- )
355
- .withParameter ( foreignPackageClassInfo .clazz )
356
- .intercept (
357
- new Implementation .Simple (
358
- new GetFieldOnArgument (
359
- getter
360
- )
361
- )
362
- );
363
342
}
364
- for ( Member setter : foreignPackageClassInfo .setters ) {
365
- final Class <?> setterType ;
366
- if ( setter instanceof Field ) {
367
- setterType = ( (Field ) setter ).getType ();
368
- }
369
- else {
370
- setterType = ( (Method ) setter ).getParameterTypes ()[0 ];
343
+ for ( Member setter : bridgeMembersClassInfo .setters ) {
344
+ if ( !Modifier .isPublic ( setter .getModifiers () ) ) {
345
+ final Class <?> setterType ;
346
+ if ( setter instanceof Field ) {
347
+ setterType = ( (Field ) setter ).getType ();
348
+ }
349
+ else {
350
+ setterType = ( (Method ) setter ).getParameterTypes ()[0 ];
351
+ }
352
+
353
+ builder = builder .defineMethod (
354
+ "set_" + setter .getName (),
355
+ TypeDescription .Generic .VOID ,
356
+ Opcodes .ACC_PROTECTED | Opcodes .ACC_STATIC
357
+ )
358
+ .withParameter ( bridgeMembersClassInfo .clazz )
359
+ .withParameter ( setterType )
360
+ .intercept (
361
+ new Implementation .Simple (
362
+ new SetFieldOnArgument (
363
+ setter
364
+ )
365
+ )
366
+ );
371
367
}
372
-
373
- builder = builder .defineMethod (
374
- "set_" + setter .getName (),
375
- TypeDescription .Generic .VOID ,
376
- Opcodes .ACC_PROTECTED | Opcodes .ACC_STATIC
377
- )
378
- .withParameter ( foreignPackageClassInfo .clazz )
379
- .withParameter ( setterType )
380
- .intercept (
381
- new Implementation .Simple (
382
- new SetFieldOnArgument (
383
- setter
384
- )
385
- )
386
- );
387
368
}
388
369
389
370
return builder ;
@@ -393,10 +374,10 @@ private Class<?> determineAccessOptimizerSuperClass(Class<?> clazz, String[] pro
393
374
for ( int j = 0 ; j < getters .length ; j ++ ) {
394
375
final Member getter = getters [j ];
395
376
final Member setter = setters [j ];
396
- if ( foreignPackageClassInfo .getters .contains ( getter ) ) {
377
+ if ( bridgeMembersClassInfo .getters .contains ( getter ) && ! Modifier . isPublic ( getter . getModifiers () ) ) {
397
378
getters [j ] = new ForeignPackageMember ( superClass , getter );
398
379
}
399
- if ( foreignPackageClassInfo .setters .contains ( setter ) ) {
380
+ if ( bridgeMembersClassInfo .setters .contains ( setter ) && ! Modifier . isPublic ( setter . getModifiers () ) ) {
400
381
setters [j ] = new ForeignPackageMember ( superClass , setter );
401
382
}
402
383
}
@@ -620,16 +601,31 @@ private boolean is64BitType(Class<?> type) {
620
601
}
621
602
}
622
603
623
- private List <ForeignPackageClassInfo > createForeignPackageClassInfos (Class <?> clazz ) {
624
- final List <ForeignPackageClassInfo > foreignPackageClassInfos = new ArrayList <>();
604
+ private List <BridgeMembersClassInfo > createBridgeMembersClassInfos (
605
+ Class <?> clazz ,
606
+ Member [] getters ,
607
+ Member [] setters ,
608
+ String [] propertyNames ) {
609
+ final List <BridgeMembersClassInfo > bridgeMembersClassInfos = new ArrayList <>();
625
610
Class <?> c = clazz .getSuperclass ();
626
611
while (c != Object .class ) {
627
- if ( !c .getPackageName ().equals ( clazz .getPackageName () ) ) {
628
- foreignPackageClassInfos .add ( new ForeignPackageClassInfo ( c ) );
612
+ final BridgeMembersClassInfo bridgeMemberClassInfo = new BridgeMembersClassInfo ( c );
613
+ for ( int i = 0 ; i < getters .length ; i ++ ) {
614
+ final Member getter = getters [i ];
615
+ final Member setter = setters [i ];
616
+ if ( getter .getDeclaringClass () == c && !Modifier .isPublic ( getter .getModifiers () )
617
+ || setter .getDeclaringClass () == c && !Modifier .isPublic ( setter .getModifiers () ) ) {
618
+ bridgeMemberClassInfo .getters .add ( getter );
619
+ bridgeMemberClassInfo .setters .add ( setter );
620
+ bridgeMemberClassInfo .propertyNames .add ( propertyNames [i ] );
621
+ }
622
+ }
623
+ if ( !bridgeMemberClassInfo .propertyNames .isEmpty () ) {
624
+ bridgeMembersClassInfos .add ( bridgeMemberClassInfo );
629
625
}
630
626
c = c .getSuperclass ();
631
627
}
632
- return foreignPackageClassInfos ;
628
+ return bridgeMembersClassInfos ;
633
629
}
634
630
635
631
public ByteBuddyProxyHelper getByteBuddyProxyHelper () {
0 commit comments