Customize reshadowing of dependencies

Refactor AP detection
This commit is contained in:
Fury_Phoenix 2023-12-16 16:45:13 -08:00
parent 83625bdfa2
commit e69ab1fef2
No known key found for this signature in database
GPG Key ID: 0595F98084987DB8
2 changed files with 84 additions and 57 deletions

View File

@ -23,6 +23,11 @@ dependencies {
implementation project(":annotations") implementation project(":annotations")
shadow project(":annotations") shadow project(":annotations")
// Shadow annotations
implementation 'net.fabricmc:sponge-mixin:0.12.5+'
implementation "net.fabricmc:fabric-loader:${rootProject.fabric_loader_version}"
implementation 'net.minecraftforge:mergetool:1.1.7'
implementation 'net.neoforged:mergetool:2.0.2'
} }
tasks.withType(JavaCompile) { tasks.withType(JavaCompile) {
@ -31,7 +36,20 @@ tasks.withType(JavaCompile) {
} }
shadowJar { shadowJar {
dependencies {
include(dependency('net.fabricmc:sponge-mixin:'))
include(dependency('net.fabricmc:fabric-loader:'))
include(dependency(':mergetool:'))
}
// shadowJar bug
include '*.jar'
include 'META-INF/services/javax.annotation.processing.Processor' include 'META-INF/services/javax.annotation.processing.Processor'
include 'org/spongepowered/asm/mixin/Mixin.class'
include 'org/fury_phoenix/**/*'
include {it.getName() == 'OnlyIn.class'}
include {it.getName() == 'Dist.class'}
include {it.getName() == 'Environment.class'}
include {it.getName() == 'EnvType.class'}
} }
spotless { spotless {

View File

@ -3,13 +3,16 @@ package org.fury_phoenix.mixinAp.annotation;
import java.lang.annotation.Annotation; import java.lang.annotation.Annotation;
import java.util.Collection; import java.util.Collection;
import java.util.HashSet; import java.util.HashSet;
import java.util.Optional; import java.util.List;
import java.util.Map;
import java.util.Set; import java.util.Set;
import java.util.function.Function;
import java.util.stream.Collectors; import java.util.stream.Collectors;
import java.util.stream.Stream; import java.util.stream.Stream;
import javax.annotation.processing.Messager; import javax.annotation.processing.Messager;
import javax.annotation.processing.ProcessingEnvironment; import javax.annotation.processing.ProcessingEnvironment;
import javax.lang.model.element.AnnotationValue;
import javax.lang.model.element.TypeElement; import javax.lang.model.element.TypeElement;
import javax.lang.model.type.TypeMirror; import javax.lang.model.type.TypeMirror;
import javax.lang.model.util.Elements; import javax.lang.model.util.Elements;
@ -18,17 +21,12 @@ import javax.tools.Diagnostic;
import org.embeddedt.modernfix.annotation.ClientOnlyMixin; import org.embeddedt.modernfix.annotation.ClientOnlyMixin;
import org.spongepowered.asm.mixin.Mixin; import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.util.asm.IAnnotationHandle;
import org.spongepowered.tools.obfuscation.AnnotatedMixinsAccessor;
import org.spongepowered.tools.obfuscation.interfaces.ITypeHandleProvider;
import org.spongepowered.tools.obfuscation.mirror.TypeHandle;
import static com.google.auto.common.AnnotationMirrors.getAnnotationValue;
import static java.util.AbstractMap.SimpleImmutableEntry; import static java.util.AbstractMap.SimpleImmutableEntry;
public class ClientMixinValidator { public class ClientMixinValidator {
private final ITypeHandleProvider typeHandleProvider;
private final Messager messager; private final Messager messager;
private final Elements elemUtils; private final Elements elemUtils;
@ -37,16 +35,33 @@ public class ClientMixinValidator {
private final boolean debug; private final boolean debug;
private static final Iterable<String> markers = Set.of( /*
"net.fabricmc.api.Environment", * @author Fury_Phoenix
"net.minecraftforge.api.distmarker.OnlyIn", * @reason This is covariant for ClientMixinValidator.markers
"net.neoforged.api.distmarker.OnlyIn"); * whilst the direct reference is not as it doesn't cover Annotation
*/
private static final Function<net.fabricmc.api.Environment, ?>
EnvironmentAccessor = net.fabricmc.api.Environment::value;
private static final Function<net.minecraftforge.api.distmarker.OnlyIn, ?>
ForgeAccessor = net.minecraftforge.api.distmarker.OnlyIn::value;
private static final Function<net.neoforged.api.distmarker.OnlyIn, ?>
NeoForgeAccessor = net.neoforged.api.distmarker.OnlyIn::value;
/*
* @author Fury_Phoenix
* @reason Partial duck-typing
*/
private static final Map
<Class<? extends Annotation>, Function<? extends Annotation, ?>>
markers = Map.of(net.fabricmc.api.Environment.class, EnvironmentAccessor,
net.minecraftforge.api.distmarker.OnlyIn.class, ForgeAccessor,
net.neoforged.api.distmarker.OnlyIn.class, NeoForgeAccessor);
private static final Collection<String> unannotatedClasses = new HashSet<>(); private static final Collection<String> unannotatedClasses = new HashSet<>();
public ClientMixinValidator(ProcessingEnvironment env) public ClientMixinValidator(ProcessingEnvironment env) {
throws ReflectiveOperationException {
typeHandleProvider = AnnotatedMixinsAccessor.getMixinAP(env);
debug = Boolean.valueOf(env.getOptions().get("org.fury_phoenix.mixinAp.validator.debug")); debug = Boolean.valueOf(env.getOptions().get("org.fury_phoenix.mixinAp.validator.debug"));
messager = env.getMessager(); messager = env.getMessager();
elemUtils = env.getElementUtils(); elemUtils = env.getElementUtils();
@ -55,14 +70,11 @@ public class ClientMixinValidator {
public boolean validateMixin(TypeElement annotatedMixinClass) { public boolean validateMixin(TypeElement annotatedMixinClass) {
return targetsClient(annotatedMixinClass) && return targetsClient(annotatedMixinClass) &&
!getAnnotationHandle(annotatedMixinClass, ClientOnlyMixin.class).exists(); (annotatedMixinClass.getAnnotation(ClientOnlyMixin.class) == null);
} }
public boolean targetsClient(TypeElement annotatedMixinClass) { public boolean targetsClient(TypeElement annotatedMixinClass) {
return targetsClient( return targetsClient(getTargets(annotatedMixinClass));
ClientMixinValidator.getTargets(
getAnnotationHandle(annotatedMixinClass, Mixin.class)
));
} }
private boolean targetsClient(Collection<?> classTargets) { private boolean targetsClient(Collection<?> classTargets) {
@ -91,14 +103,15 @@ public class ClientMixinValidator {
} }
private boolean isClientMarked(TypeElement te) { private boolean isClientMarked(TypeElement te) {
for (var marker : getPlatformMarkers(markers)) { for (var entry : markers.entrySet()) {
IAnnotationHandle handle = getAnnotationHandle(te, marker); var marker = te.getAnnotation(entry.getKey());
if(!handle.exists()) continue; if(marker == null) continue;
String[] enumValue = handle.getValue("value"); // Pretend to accept Annotations
if(enumValue==null) continue; @SuppressWarnings("unchecked")
boolean isClient = ((Function<Annotation, ?>)entry.getValue())
return enumValue[1].equals("CLIENT"); .apply(marker).toString().equals("CLIENT");
return isClient;
} }
if(debug && unannotatedClasses.add(te.toString())) { if(debug && unannotatedClasses.add(te.toString())) {
messager.printMessage(Diagnostic.Kind.WARNING, messager.printMessage(Diagnostic.Kind.WARNING,
@ -117,9 +130,8 @@ public class ClientMixinValidator {
getEntry(TypeElement annotatedMixinClass) { getEntry(TypeElement annotatedMixinClass) {
return new SimpleImmutableEntry<>( return new SimpleImmutableEntry<>(
annotatedMixinClass.getQualifiedName(), annotatedMixinClass.getQualifiedName(),
ClientMixinValidator.getTargets( getTargets(annotatedMixinClass)
getAnnotationHandle(annotatedMixinClass, Mixin.class) .stream()
).stream()
.filter(this::targetsClient) .filter(this::targetsClient)
.map(Object::toString) .map(Object::toString)
.map(ClientMixinValidator::toSourceString) .map(ClientMixinValidator::toSourceString)
@ -127,38 +139,35 @@ public class ClientMixinValidator {
); );
} }
private TypeHandle getTypeHandle(Object annotatedClass) { private Collection<Object> getTargets(TypeElement mixinAnnotatedClass) {
return typeHandleProvider.getTypeHandle(annotatedClass); Collection<? extends TypeMirror> clzsses = Set.of();
} Collection<? extends String> imaginaries = Set.of();
TypeMirror MixinElement = elemUtils.getTypeElement(Mixin.class.getName()).asType();
private IAnnotationHandle getAnnotationHandle for (var annotationMirror : mixinAnnotatedClass.getAnnotationMirrors()) {
(Object annotatedClass, Class<? extends Annotation> annotation) { if(!annotationMirror.getAnnotationType().equals(MixinElement))
return getTypeHandle(annotatedClass).getAnnotation(annotation); continue;
}
private static Collection<Object> getTargets(IAnnotationHandle mixinAnnotation) {
Collection<? extends TypeMirror> clzss = mixinAnnotation.getList("value");
Collection<? extends String> imaginary = mixinAnnotation.getList("targets");
return Stream.of(clzss, imaginary)
.flatMap(Collection::stream)
.collect(Collectors.toList());
}
private static Iterable<Class<? extends Annotation>>
getPlatformMarkers(Iterable<String> markers) {
Set<Class<? extends Annotation>> platformClasses = new HashSet<>();
for(var marker : markers) {
getMarkerClass(marker).ifPresent(platformClasses::add);
}
return platformClasses;
}
@SuppressWarnings("unchecked") @SuppressWarnings("unchecked")
private static Optional<Class<? extends Annotation>> getMarkerClass(String marker) { var wrappedClzss = (List<? extends AnnotationValue>)
try { getAnnotationValue(annotationMirror, "value").getValue();
return Optional.of((Class<? extends Annotation>)Class.forName(marker));
} catch (ClassNotFoundException e) {} clzsses = wrappedClzss.stream()
return Optional.empty(); .map(AnnotationValue::getValue)
.map(TypeMirror.class::cast)
.collect(Collectors.toSet());
@SuppressWarnings("unchecked")
var wrappedStrings = (List<? extends AnnotationValue>)
getAnnotationValue(annotationMirror, "targets").getValue();
imaginaries = wrappedStrings.stream()
.map(AnnotationValue::getValue)
.map(String.class::cast)
.collect(Collectors.toSet());
}
return Stream.of(clzsses, imaginaries)
.flatMap(Collection::stream)
.collect(Collectors.toList());
} }
public static String toSourceString(String bytecodeName) { public static String toSourceString(String bytecodeName) {