feat: matching the erasure bridge should be optional

This commit is contained in:
zaaarf 2023-04-12 00:38:55 +02:00
parent 61fa43fb8d
commit 524818a378
No known key found for this signature in database
GPG key ID: 82240E075E31FA4C
2 changed files with 18 additions and 12 deletions

View file

@ -44,4 +44,12 @@ public @interface Target {
* @since 0.3.0 * @since 0.3.0
*/ */
boolean strict() default true; boolean strict() default true;
/**
* When set to true, tells the processor to match the synthetic "bridge" method
* generated by the compiler to handle type erasure.
* @return whether the bridge method should be targeted instead of the actual method
* @since 0.5.2
*/
boolean bridge() default false;
} }

View file

@ -59,13 +59,14 @@ public class MethodContainer {
* @param parent the {@link ClassContainer} representing the parent * @param parent the {@link ClassContainer} representing the parent
* @param name the fully-qualified name of the target method * @param name the fully-qualified name of the target method
* @param descriptor the descriptor of the target method * @param descriptor the descriptor of the target method
* @param strict whether the matching should be strict (see {@link Target#strict()} for more info). * @param strict whether the matching should be strict (see {@link Target#strict()} for more info)
* @param bridge whether the "bridge" should be matched isntead (see {@link Target#bridge()} for more info)
* @param env the {@link ProcessingEnvironment} to perform the operation in * @param env the {@link ProcessingEnvironment} to perform the operation in
* @param mapper the {@link ObfuscationMapper} to be used, may be null * @param mapper the {@link ObfuscationMapper} to be used, may be null
*/ */
private MethodContainer( private MethodContainer(
ClassContainer parent, String name, String descriptor, ClassContainer parent, String name, String descriptor, boolean strict,
boolean strict, ProcessingEnvironment env, ObfuscationMapper mapper) { boolean bridge, ProcessingEnvironment env, ObfuscationMapper mapper) {
this.parent = parent; this.parent = parent;
if(parent.elem == null) { //unverified if(parent.elem == null) { //unverified
if(descriptor == null) if(descriptor == null)
@ -74,13 +75,10 @@ public class MethodContainer {
this.name = name; this.name = name;
this.descriptor = descriptor; this.descriptor = descriptor;
} else { } else {
this.elem = findOverloadedMethod( //to prevent type erasure from messing it all up ExecutableElement tmp = (ExecutableElement) findMember(
(TypeElement) this.parent.elem, parent, name, descriptor, descriptor != null && strict,false, env
(ExecutableElement) findMember(
parent, name, descriptor, descriptor != null && strict,false, env
), env
); );
this.elem = bridge ? findOverloadedMethod((TypeElement) this.parent.elem, tmp, env) : tmp;
this.name = this.elem.getSimpleName().toString(); this.name = this.elem.getSimpleName().toString();
this.descriptor = descriptorFromExecutableElement(this.elem, env); this.descriptor = descriptorFromExecutableElement(this.elem, env);
} }
@ -108,13 +106,13 @@ public class MethodContainer {
f, env, mapper f, env, mapper
); );
String name = t != null && !t.methodName().equals("") String name = !t.methodName().equals("")
? t.methodName() //name was specified in target ? t.methodName() //name was specified in target
: stub.getSimpleName().toString(); : stub.getSimpleName().toString();
String descriptor = t != null && t.strict() String descriptor = t.strict()
? descriptorFromExecutableElement(stub, env) ? descriptorFromExecutableElement(stub, env)
: null; : null;
return new MethodContainer(parent, name, descriptor, t != null && t.strict(), env, mapper); return new MethodContainer(parent, name, descriptor, t.strict(), t.bridge(), env, mapper);
} }
} }