diff --git a/build.gradle b/build.gradle index af0cc43..82384ce 100644 --- a/build.gradle +++ b/build.gradle @@ -50,6 +50,8 @@ dependencies { implementation ('net.fabricmc:tiny-remapper:0.3.0.70') implementation ('net.fabricmc:tiny-mappings-parser:0.2.2.14') + implementation 'net.fabricmc:access-widener:1.0.0' + implementation ('net.fabricmc:lorenz-tiny:2.0.0+build.2') { transitive = false } diff --git a/src/main/java/net/fabricmc/loom/util/Constants.java b/src/main/java/net/fabricmc/loom/util/Constants.java index e5b3a77..7caa865 100644 --- a/src/main/java/net/fabricmc/loom/util/Constants.java +++ b/src/main/java/net/fabricmc/loom/util/Constants.java @@ -27,6 +27,7 @@ package net.fabricmc.loom.util; import java.util.List; import com.google.common.collect.ImmutableList; +import org.objectweb.asm.Opcodes; public class Constants { public static final String LIBRARIES_BASE = "https://libraries.minecraft.net/"; @@ -35,6 +36,8 @@ public class Constants { public static final String SYSTEM_ARCH = System.getProperty("os.arch").equals("64") ? "64" : "32"; + public static final int ASM_VERSION = Opcodes.ASM9; + public static final List MOD_COMPILE_ENTRIES = ImmutableList.of( new RemappedConfigurationEntry("modCompile", "compile", true, "compile"), new RemappedConfigurationEntry("modApi", "api", true, "compile"), diff --git a/src/main/java/net/fabricmc/loom/util/LineNumberRemapper.java b/src/main/java/net/fabricmc/loom/util/LineNumberRemapper.java index 95fd976..74cb0d6 100644 --- a/src/main/java/net/fabricmc/loom/util/LineNumberRemapper.java +++ b/src/main/java/net/fabricmc/loom/util/LineNumberRemapper.java @@ -45,7 +45,6 @@ import org.objectweb.asm.ClassVisitor; import org.objectweb.asm.ClassWriter; import org.objectweb.asm.Label; import org.objectweb.asm.MethodVisitor; -import org.objectweb.asm.Opcodes; import net.fabricmc.loom.util.progress.ProgressLogger; @@ -124,7 +123,7 @@ public class LineNumberRemapper { ClassReader reader = new ClassReader(is); ClassWriter writer = new ClassWriter(0); - reader.accept(new LineNumberVisitor(Opcodes.ASM7, writer, lineMap.get(idx)), 0); + reader.accept(new LineNumberVisitor(Constants.ASM_VERSION, writer, lineMap.get(idx)), 0); Files.write(dst, writer.toByteArray()); } } diff --git a/src/main/java/net/fabricmc/loom/util/ModProcessor.java b/src/main/java/net/fabricmc/loom/util/ModProcessor.java index bacfca9..1932f21 100644 --- a/src/main/java/net/fabricmc/loom/util/ModProcessor.java +++ b/src/main/java/net/fabricmc/loom/util/ModProcessor.java @@ -51,11 +51,13 @@ import org.zeroturnaround.zip.ZipUtil; import org.zeroturnaround.zip.transform.StringZipEntryTransformer; import org.zeroturnaround.zip.transform.ZipEntryTransformerEntry; +import net.fabricmc.accesswidener.AccessWidener; +import net.fabricmc.accesswidener.AccessWidenerReader; +import net.fabricmc.accesswidener.AccessWidenerRemapper; +import net.fabricmc.accesswidener.AccessWidenerWriter; import net.fabricmc.loom.LoomGradleExtension; import net.fabricmc.loom.providers.MappingsProvider; import net.fabricmc.loom.providers.MinecraftMappedProvider; -import net.fabricmc.loom.util.accesswidener.AccessWidener; -import net.fabricmc.loom.util.accesswidener.AccessWidenerRemapper; import net.fabricmc.loom.processors.dependency.ModDependencyInfo; import net.fabricmc.tinyremapper.TinyRemapper; import net.fabricmc.tinyremapper.InputTag; @@ -109,13 +111,15 @@ public class ModProcessor { private static byte[] remapAccessWidener(byte[] input, Remapper remapper) { try (BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(new ByteArrayInputStream(input), StandardCharsets.UTF_8))) { AccessWidener accessWidener = new AccessWidener(); - accessWidener.read(bufferedReader); + AccessWidenerReader accessWidenerReader = new AccessWidenerReader(accessWidener); + accessWidenerReader.read(bufferedReader); AccessWidenerRemapper accessWidenerRemapper = new AccessWidenerRemapper(accessWidener, remapper, "named"); AccessWidener remapped = accessWidenerRemapper.remap(); + AccessWidenerWriter accessWidenerWriter = new AccessWidenerWriter(remapped); try (StringWriter writer = new StringWriter()) { - remapped.write(writer); + accessWidenerWriter.write(writer); return writer.toString().getBytes(StandardCharsets.UTF_8); } } catch (IOException e) { diff --git a/src/main/java/net/fabricmc/loom/util/accesswidener/AccessWidener.java b/src/main/java/net/fabricmc/loom/util/accesswidener/AccessWidener.java deleted file mode 100644 index df061a6..0000000 --- a/src/main/java/net/fabricmc/loom/util/accesswidener/AccessWidener.java +++ /dev/null @@ -1,477 +0,0 @@ -/* - * This file is part of fabric-loom, licensed under the MIT License (MIT). - * - * Copyright (c) 2016, 2017, 2018 FabricMC - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in all - * copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE - * SOFTWARE. - */ - -package net.fabricmc.loom.util.accesswidener; - -import java.io.BufferedReader; -import java.io.IOException; -import java.io.StringWriter; -import java.util.ArrayList; -import java.util.HashMap; -import java.util.LinkedHashSet; -import java.util.List; -import java.util.Locale; -import java.util.Map; -import java.util.Set; - -import org.objectweb.asm.Opcodes; - -import net.fabricmc.mappings.EntryTriple; - -public class AccessWidener { - public String namespace; - public Map classAccess = new HashMap<>(); - public Map methodAccess = new HashMap<>(); - public Map fieldAccess = new HashMap<>(); - private final Set classes = new LinkedHashSet<>(); - - public void read(BufferedReader reader) throws IOException { - String headerStr = reader.readLine(); - - if (headerStr == null) { - throw new RuntimeException("Cannot read empty or invalid access widener"); - } - - String[] header = headerStr.split("\\s+"); - - if (header.length != 3 || !header[0].equals("accessWidener")) { - throw new UnsupportedOperationException("Invalid access access widener header"); - } - - if (!header[1].equals("v1")) { - throw new RuntimeException(String.format("Unsupported access widener format (%s)", header[1])); - } - - if (namespace != null) { - if (!namespace.equals(header[2])) { - throw new RuntimeException(String.format("Namespace mismatch, expected %s got %s", namespace, header[2])); - } - } - - namespace = header[2]; - - String line; - - Set targets = new LinkedHashSet<>(); - - while ((line = reader.readLine()) != null) { - // Comment handling - int commentPos = line.indexOf('#'); - - if (commentPos >= 0) { - line = line.substring(0, commentPos).trim(); - } - - if (line.isEmpty()) continue; - - String[] split = line.split("\\s+"); - - if (split.length != 3 && split.length != 5) { - throw new RuntimeException(String.format("Invalid line (%s)", line)); - } - - String access = split[0]; - - targets.add(split[2].replaceAll("/", ".")); - - switch (split[1]) { - case "class": - if (split.length != 3) { - throw new RuntimeException(String.format("Expected (\tclass\t) got (%s)", line)); - } - - classAccess.put(split[2], applyAccess(access, classAccess.getOrDefault(split[2], ClassAccess.DEFAULT), null)); - break; - case "field": - if (split.length != 5) { - throw new RuntimeException(String.format("Expected (\tfield\t\t\t) got (%s)", line)); - } - - addOrMerge(fieldAccess, new EntryTriple(split[2], split[3], split[4]), access, FieldAccess.DEFAULT); - break; - case "method": - if (split.length != 5) { - throw new RuntimeException(String.format("Expected (\tmethod\t\t\t) got (%s)", line)); - } - - addOrMerge(methodAccess, new EntryTriple(split[2], split[3], split[4]), access, MethodAccess.DEFAULT); - break; - default: - throw new UnsupportedOperationException("Unsupported type " + split[1]); - } - } - - Set parentClasses = new LinkedHashSet<>(); - - //Also transform all parent classes - for (String clazz : targets) { - while (clazz.contains("$")) { - clazz = clazz.substring(0, clazz.lastIndexOf("$")); - parentClasses.add(clazz); - } - } - - classes.addAll(targets); - classes.addAll(parentClasses); - } - - // Could possibly be cleaner but should do its job for now - public void write(StringWriter writer) { - writer.write("accessWidener\tv1\t"); - writer.write(namespace); - writer.write("\n"); - - for (Map.Entry entry : classAccess.entrySet()) { - for (String s : getAccesses(entry.getValue())) { - writer.write(s); - writer.write("\tclass\t"); - writer.write(entry.getKey()); - writer.write("\n"); - } - } - - for (Map.Entry entry : methodAccess.entrySet()) { - writeEntry(writer, "method", entry.getKey(), entry.getValue()); - } - - for (Map.Entry entry : fieldAccess.entrySet()) { - writeEntry(writer, "field", entry.getKey(), entry.getValue()); - } - } - - private void writeEntry(StringWriter writer, String type, EntryTriple entryTriple, Access access) { - for (String s : getAccesses(access)) { - writer.write(s); - writer.write("\t"); - writer.write(type); - writer.write("\t"); - writer.write(entryTriple.getOwner()); - writer.write("\t"); - writer.write(entryTriple.getName()); - writer.write("\t"); - writer.write(entryTriple.getDesc()); - writer.write("\n"); - } - } - - private List getAccesses(Access access) { - List accesses = new ArrayList<>(); - - if (access == ClassAccess.ACCESSIBLE || access == MethodAccess.ACCESSIBLE || access == FieldAccess.ACCESSIBLE || access == MethodAccess.ACCESSIBLE_EXTENDABLE || access == ClassAccess.ACCESSIBLE_EXTENDABLE || access == FieldAccess.ACCESSIBLE_MUTABLE) { - accesses.add("accessible"); - } - - if (access == ClassAccess.EXTENDABLE || access == MethodAccess.EXTENDABLE || access == MethodAccess.ACCESSIBLE_EXTENDABLE || access == ClassAccess.ACCESSIBLE_EXTENDABLE) { - accesses.add("extendable"); - } - - if (access == FieldAccess.MUTABLE || access == FieldAccess.ACCESSIBLE_MUTABLE) { - accesses.add("mutable"); - } - - return accesses; - } - - void addOrMerge(Map map, EntryTriple entry, Access access) { - if (entry == null || access == null) { - throw new RuntimeException("Input entry or access is null"); - } - - Access merged = null; - - if (access instanceof ClassAccess) { - merged = ClassAccess.DEFAULT; - } else if (access instanceof MethodAccess) { - merged = MethodAccess.DEFAULT; - } else if (access instanceof FieldAccess) { - merged = FieldAccess.DEFAULT; - } - - merged = mergeAccess(merged, access); - - map.put(entry, merged); - } - - void addOrMerge(Map map, EntryTriple entry, String access, Access defaultAccess) { - if (entry == null || access == null) { - throw new RuntimeException("Input entry or access is null"); - } - - map.put(entry, applyAccess(access, map.getOrDefault(entry, defaultAccess), entry)); - } - - public void merge(AccessWidener other) { - if (namespace == null) { - namespace = other.namespace; - } else if (!namespace.equals(other.namespace)) { - throw new RuntimeException("Namespace mismatch"); - } - - for (Map.Entry entry : other.classAccess.entrySet()) { - if (classAccess.containsKey(entry.getKey())) { - classAccess.replace(entry.getKey(), mergeAccess(classAccess.get(entry.getKey()), entry.getValue())); - } else { - classAccess.put(entry.getKey(), entry.getValue()); - } - } - - for (Map.Entry entry : other.methodAccess.entrySet()) { - addOrMerge(methodAccess, entry.getKey(), entry.getValue()); - } - - for (Map.Entry entry : other.fieldAccess.entrySet()) { - addOrMerge(fieldAccess, entry.getKey(), entry.getValue()); - } - } - - private Access applyAccess(String input, Access access, EntryTriple entryTriple) { - switch (input.toLowerCase(Locale.ROOT)) { - case "accessible": - makeClassAccessible(entryTriple); - return access.makeAccessible(); - case "extendable": - makeClassExtendable(entryTriple); - return access.makeExtendable(); - case "mutable": - return access.makeMutable(); - default: - throw new UnsupportedOperationException("Unknown access type:" + input); - } - } - - private void makeClassAccessible(EntryTriple entryTriple) { - if (entryTriple == null) return; - classAccess.put(entryTriple.getOwner(), applyAccess("accessible", classAccess.getOrDefault(entryTriple.getOwner(), ClassAccess.DEFAULT), null)); - } - - private void makeClassExtendable(EntryTriple entryTriple) { - if (entryTriple == null) return; - classAccess.put(entryTriple.getOwner(), applyAccess("extendable", classAccess.getOrDefault(entryTriple.getOwner(), ClassAccess.DEFAULT), null)); - } - - private static Access mergeAccess(Access a, Access b) { - Access access = a; - - if (b == ClassAccess.ACCESSIBLE || b == MethodAccess.ACCESSIBLE || b == FieldAccess.ACCESSIBLE || b == MethodAccess.ACCESSIBLE_EXTENDABLE || b == ClassAccess.ACCESSIBLE_EXTENDABLE || b == FieldAccess.ACCESSIBLE_MUTABLE) { - access = access.makeAccessible(); - } - - if (b == ClassAccess.EXTENDABLE || b == MethodAccess.EXTENDABLE || b == MethodAccess.ACCESSIBLE_EXTENDABLE || b == ClassAccess.ACCESSIBLE_EXTENDABLE) { - access = access.makeExtendable(); - } - - if (b == FieldAccess.MUTABLE || b == FieldAccess.ACCESSIBLE_MUTABLE) { - access = access.makeMutable(); - } - - return access; - } - - public Access getClassAccess(String className) { - return classAccess.getOrDefault(className, ClassAccess.DEFAULT); - } - - public Access getFieldAccess(EntryTriple entryTriple) { - return fieldAccess.getOrDefault(entryTriple, FieldAccess.DEFAULT); - } - - public Access getMethodAccess(EntryTriple entryTriple) { - return methodAccess.getOrDefault(entryTriple, MethodAccess.DEFAULT); - } - - public Set getTargets() { - return classes; - } - - private static int makePublic(int i) { - return (i & ~(Opcodes.ACC_PRIVATE | Opcodes.ACC_PROTECTED)) | Opcodes.ACC_PUBLIC; - } - - private static int makeProtected(int i) { - if ((i & Opcodes.ACC_PUBLIC) != 0) { - // Return i if public - return i; - } - - return (i & ~(Opcodes.ACC_PRIVATE)) | Opcodes.ACC_PROTECTED; - } - - private static int makeFinalIfPrivate(int access, String name, int ownerAccess) { - // Dont make constructors final - if (name.equals("")) { - return access; - } - - // Skip interface and static methods - if ((ownerAccess & Opcodes.ACC_INTERFACE) != 0 || (access & Opcodes.ACC_STATIC) != 0) { - return access; - } - - if ((access & Opcodes.ACC_PRIVATE) != 0) { - return access | Opcodes.ACC_FINAL; - } - - return access; - } - - private static int removeFinal(int i) { - return i & ~Opcodes.ACC_FINAL; - } - - public interface Access extends AccessOperator { - Access makeAccessible(); - - Access makeExtendable(); - - Access makeMutable(); - } - - public enum ClassAccess implements Access { - DEFAULT((access, name, ownerAccess) -> access), - ACCESSIBLE((access, name, ownerAccess) -> makePublic(access)), - EXTENDABLE((access, name, ownerAccess) -> makePublic(removeFinal(access))), - ACCESSIBLE_EXTENDABLE((access, name, ownerAccess) -> makePublic(removeFinal(access))); - - private final AccessOperator operator; - - ClassAccess(AccessOperator operator) { - this.operator = operator; - } - - @Override - public Access makeAccessible() { - if (this == EXTENDABLE || this == ACCESSIBLE_EXTENDABLE) { - return ACCESSIBLE_EXTENDABLE; - } - - return ACCESSIBLE; - } - - @Override - public Access makeExtendable() { - if (this == ACCESSIBLE || this == ACCESSIBLE_EXTENDABLE) { - return ACCESSIBLE_EXTENDABLE; - } - - return EXTENDABLE; - } - - @Override - public Access makeMutable() { - throw new UnsupportedOperationException("Classes cannot be made mutable"); - } - - @Override - public int apply(int access, String targetName, int ownerAccess) { - return operator.apply(access, targetName, ownerAccess); - } - } - - public enum MethodAccess implements Access { - DEFAULT((access, name, ownerAccess) -> access), - ACCESSIBLE((access, name, ownerAccess) -> makePublic(makeFinalIfPrivate(access, name, ownerAccess))), - EXTENDABLE((access, name, ownerAccess) -> makeProtected(removeFinal(access))), - ACCESSIBLE_EXTENDABLE((access, name, owner) -> makePublic(removeFinal(access))); - - private final AccessOperator operator; - - MethodAccess(AccessOperator operator) { - this.operator = operator; - } - - @Override - public Access makeAccessible() { - if (this == EXTENDABLE || this == ACCESSIBLE_EXTENDABLE) { - return ACCESSIBLE_EXTENDABLE; - } - - return ACCESSIBLE; - } - - @Override - public Access makeExtendable() { - if (this == ACCESSIBLE || this == ACCESSIBLE_EXTENDABLE) { - return ACCESSIBLE_EXTENDABLE; - } - - return EXTENDABLE; - } - - @Override - public Access makeMutable() { - throw new UnsupportedOperationException("Methods cannot be made mutable"); - } - - @Override - public int apply(int access, String targetName, int ownerAccess) { - return operator.apply(access, targetName, ownerAccess); - } - } - - public enum FieldAccess implements Access { - DEFAULT((access, name, ownerAccess) -> access), - ACCESSIBLE((access, name, ownerAccess) -> makePublic(access)), - MUTABLE((access, name, ownerAccess) -> removeFinal(access)), - ACCESSIBLE_MUTABLE((access, name, ownerAccess) -> makePublic(removeFinal(access))); - - private final AccessOperator operator; - - FieldAccess(AccessOperator operator) { - this.operator = operator; - } - - @Override - public Access makeAccessible() { - if (this == MUTABLE || this == ACCESSIBLE_MUTABLE) { - return ACCESSIBLE_MUTABLE; - } - - return ACCESSIBLE; - } - - @Override - public Access makeExtendable() { - throw new UnsupportedOperationException("Fields cannot be made extendable"); - } - - @Override - public Access makeMutable() { - if (this == ACCESSIBLE || this == ACCESSIBLE_MUTABLE) { - return ACCESSIBLE_MUTABLE; - } - - return MUTABLE; - } - - @Override - public int apply(int access, String targetName, int ownerAccess) { - return operator.apply(access, targetName, ownerAccess); - } - } - - @FunctionalInterface - public interface AccessOperator { - int apply(int access, String targetName, int ownerAccess); - } -} diff --git a/src/main/java/net/fabricmc/loom/util/accesswidener/AccessWidenerJarProcessor.java b/src/main/java/net/fabricmc/loom/util/accesswidener/AccessWidenerJarProcessor.java index 4770c38..aa02c2d 100644 --- a/src/main/java/net/fabricmc/loom/util/accesswidener/AccessWidenerJarProcessor.java +++ b/src/main/java/net/fabricmc/loom/util/accesswidener/AccessWidenerJarProcessor.java @@ -41,23 +41,26 @@ import org.gradle.api.Project; import org.objectweb.asm.ClassReader; import org.objectweb.asm.ClassVisitor; import org.objectweb.asm.ClassWriter; -import org.objectweb.asm.FieldVisitor; -import org.objectweb.asm.MethodVisitor; -import org.objectweb.asm.Opcodes; import org.objectweb.asm.commons.Remapper; import org.zeroturnaround.zip.ZipUtil; import org.zeroturnaround.zip.transform.ByteArrayZipEntryTransformer; import org.zeroturnaround.zip.transform.ZipEntryTransformer; import org.zeroturnaround.zip.transform.ZipEntryTransformerEntry; +import net.fabricmc.accesswidener.AccessWidener; +import net.fabricmc.accesswidener.AccessWidenerRemapper; +import net.fabricmc.accesswidener.AccessWidenerReader; +import net.fabricmc.accesswidener.AccessWidenerVisitor; +import net.fabricmc.accesswidener.AccessWidenerWriter; import net.fabricmc.loom.LoomGradleExtension; import net.fabricmc.loom.processors.JarProcessor; +import net.fabricmc.loom.util.Constants; import net.fabricmc.loom.util.Checksum; -import net.fabricmc.mappings.EntryTriple; import net.fabricmc.tinyremapper.TinyRemapper; public class AccessWidenerJarProcessor implements JarProcessor { private AccessWidener accessWidener = new AccessWidener(); + private AccessWidenerReader accessWidenerReader = new AccessWidenerReader(accessWidener); private final Project project; private byte[] inputHash; @@ -76,13 +79,13 @@ public class AccessWidenerJarProcessor implements JarProcessor { inputHash = Checksum.sha256(loomGradleExtension.accessWidener); try (BufferedReader reader = new BufferedReader(new FileReader(loomGradleExtension.accessWidener))) { - accessWidener.read(reader); + accessWidenerReader.read(reader); } catch (IOException e) { throw new RuntimeException("Failed to read project access widener file"); } //Remap accessWidener if its not named, allows for AE's to be written in intermediary - if (!accessWidener.namespace.equals("named")) { + if (!accessWidener.getNamespace().equals("named")) { try { TinyRemapper tinyRemapper = loomGradleExtension.getMinecraftMappedProvider().getTinyRemapper("official", "named"); tinyRemapper.readClassPath(loomGradleExtension.getMinecraftMappedProvider().getRemapClasspath()); @@ -116,10 +119,11 @@ public class AccessWidenerJarProcessor implements JarProcessor { protected byte[] transform(ZipEntry zipEntry, byte[] input) { ClassReader reader = new ClassReader(input); ClassWriter writer = new ClassWriter(0); + ClassVisitor classVisitor = AccessWidenerVisitor.createClassVisitor(Constants.ASM_VERSION, writer, accessWidener); project.getLogger().lifecycle("Applying access widener to " + className); - reader.accept(new AccessTransformer(writer), 0); + reader.accept(classVisitor, 0); return writer.toByteArray(); } }; @@ -145,9 +149,10 @@ public class AccessWidenerJarProcessor implements JarProcessor { public byte[] getRemappedAccessWidener(Remapper asmRemapper) throws IOException { AccessWidenerRemapper remapper = new AccessWidenerRemapper(accessWidener, asmRemapper, "intermediary"); AccessWidener remapped = remapper.remap(); + AccessWidenerWriter accessWidenerWriter = new AccessWidenerWriter(remapped); try (StringWriter writer = new StringWriter()) { - remapped.write(writer); + accessWidenerWriter.write(writer); return writer.toString().getBytes(); } } @@ -178,78 +183,4 @@ public class AccessWidenerJarProcessor implements JarProcessor { return !Arrays.equals(inputHash, hash); // TODO how do we know if the current jar as the correct access applied? save the hash of the input? } - - private class AccessTransformer extends ClassVisitor { - private String className; - private int classAccess; - - private AccessTransformer(ClassVisitor classVisitor) { - super(Opcodes.ASM7, classVisitor); - } - - @Override - public void visit(int version, int access, String name, String signature, String superName, String[] interfaces) { - className = name; - classAccess = access; - super.visit( - version, - accessWidener.getClassAccess(name).apply(access, name, classAccess), - name, - signature, - superName, - interfaces - ); - } - - @Override - public void visitInnerClass(String name, String outerName, String innerName, int access) { - super.visitInnerClass( - name, - outerName, - innerName, - accessWidener.getClassAccess(name).apply(access, name, classAccess) - ); - } - - @Override - public FieldVisitor visitField(int access, String name, String descriptor, String signature, Object value) { - return super.visitField( - accessWidener.getFieldAccess(new EntryTriple(className, name, descriptor)).apply(access, name, classAccess), - name, - descriptor, - signature, - value - ); - } - - @Override - public MethodVisitor visitMethod(int access, String name, String descriptor, String signature, String[] exceptions) { - return new AccessWidenerMethodVisitor(super.visitMethod( - accessWidener.getMethodAccess(new EntryTriple(className, name, descriptor)).apply(access, name, classAccess), - name, - descriptor, - signature, - exceptions - )); - } - - private class AccessWidenerMethodVisitor extends MethodVisitor { - AccessWidenerMethodVisitor(MethodVisitor methodVisitor) { - super(Opcodes.ASM7, methodVisitor); - } - - @Override - public void visitMethodInsn(int opcode, String owner, String name, String descriptor, boolean isInterface) { - if (opcode == Opcodes.INVOKESPECIAL && owner.equals(className) && !name.equals("")) { - AccessWidener.Access methodAccess = accessWidener.getMethodAccess(new EntryTriple(owner, name, descriptor)); - - if (methodAccess != AccessWidener.MethodAccess.DEFAULT) { - opcode = Opcodes.INVOKEVIRTUAL; - } - } - - super.visitMethodInsn(opcode, owner, name, descriptor, isInterface); - } - } - } } diff --git a/src/main/java/net/fabricmc/loom/util/accesswidener/AccessWidenerRemapper.java b/src/main/java/net/fabricmc/loom/util/accesswidener/AccessWidenerRemapper.java deleted file mode 100644 index 20dbf5f..0000000 --- a/src/main/java/net/fabricmc/loom/util/accesswidener/AccessWidenerRemapper.java +++ /dev/null @@ -1,83 +0,0 @@ -/* - * This file is part of fabric-loom, licensed under the MIT License (MIT). - * - * Copyright (c) 2016, 2017, 2018 FabricMC - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in all - * copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE - * SOFTWARE. - */ - -package net.fabricmc.loom.util.accesswidener; - -import java.util.Map; - -import org.objectweb.asm.commons.Remapper; - -import net.fabricmc.mappings.EntryTriple; - -public class AccessWidenerRemapper { - private final AccessWidener input; - private final String to; - private final Remapper remapper; - - public AccessWidenerRemapper(AccessWidener input, Remapper remapper, String to) { - this.input = input; - this.to = to; - this.remapper = remapper; - } - - public AccessWidener remap() { - // Dont remap if we dont need to - if (input.namespace.equals(to)) { - return input; - } - - AccessWidener remapped = new AccessWidener(); - remapped.namespace = to; - - for (Map.Entry entry : input.classAccess.entrySet()) { - remapped.classAccess.put(remapper.map(entry.getKey()), entry.getValue()); - } - - for (Map.Entry entry : input.methodAccess.entrySet()) { - remapped.addOrMerge(remapped.methodAccess, remapMethod(entry.getKey()), entry.getValue()); - } - - for (Map.Entry entry : input.fieldAccess.entrySet()) { - remapped.addOrMerge(remapped.fieldAccess, remapField(entry.getKey()), entry.getValue()); - } - - return remapped; - } - - private EntryTriple remapMethod(EntryTriple entryTriple) { - return new EntryTriple( - remapper.map(entryTriple.getOwner()), - remapper.mapMethodName(entryTriple.getOwner(), entryTriple.getName(), entryTriple.getDesc()), - remapper.mapDesc(entryTriple.getDesc()) - ); - } - - private EntryTriple remapField(EntryTriple entryTriple) { - return new EntryTriple( - remapper.map(entryTriple.getOwner()), - remapper.mapFieldName(entryTriple.getOwner(), entryTriple.getName(), entryTriple.getDesc()), - remapper.mapDesc(entryTriple.getDesc()) - ); - } -}