aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorshedaniel <daniel@shedaniel.me>2021-05-08 12:50:17 +0800
committershedaniel <daniel@shedaniel.me>2021-05-08 12:50:17 +0800
commit3f576a44abe93e6f85cd2abe36f5a4a9ec415c9e (patch)
tree10b3a44809f41b979767b293bb98bbfb1b1bedfc /src
parentd91d7c096ca33d2ba91fb22065b331f102014053 (diff)
downloadarchitectury-loom-3f576a44abe93e6f85cd2abe36f5a4a9ec415c9e.tar.gz
architectury-loom-3f576a44abe93e6f85cd2abe36f5a4a9ec415c9e.tar.bz2
architectury-loom-3f576a44abe93e6f85cd2abe36f5a4a9ec415c9e.zip
Migration Mappings Detection
Still having issues with source locations, would need to check it out first Signed-off-by: shedaniel <daniel@shedaniel.me>
Diffstat (limited to 'src')
-rw-r--r--src/main/java/net/fabricmc/loom/LoomGradleExtension.java3
-rw-r--r--src/main/java/net/fabricmc/loom/configuration/CompileConfiguration.java3
-rw-r--r--src/main/java/net/fabricmc/loom/configuration/LoomDependencyManager.java2
-rw-r--r--src/main/java/net/fabricmc/loom/configuration/providers/forge/FieldMigratedMappingsProvider.java258
-rw-r--r--src/main/java/net/fabricmc/loom/configuration/providers/forge/MinecraftPatchedProvider.java59
-rw-r--r--src/main/java/net/fabricmc/loom/configuration/providers/forge/PatchProvider.java18
-rw-r--r--src/main/java/net/fabricmc/loom/configuration/providers/mappings/MappingsProvider.java42
-rw-r--r--src/main/java/net/fabricmc/loom/util/ThreadingUtils.java6
-rw-r--r--src/main/java/net/fabricmc/loom/util/srg/SpecialSourceExecutor.java2
9 files changed, 344 insertions, 49 deletions
diff --git a/src/main/java/net/fabricmc/loom/LoomGradleExtension.java b/src/main/java/net/fabricmc/loom/LoomGradleExtension.java
index 0fcdec86..039d5991 100644
--- a/src/main/java/net/fabricmc/loom/LoomGradleExtension.java
+++ b/src/main/java/net/fabricmc/loom/LoomGradleExtension.java
@@ -60,6 +60,7 @@ import net.fabricmc.loom.configuration.launch.LaunchProviderSettings;
import net.fabricmc.loom.configuration.processors.JarProcessor;
import net.fabricmc.loom.configuration.processors.JarProcessorManager;
import net.fabricmc.loom.configuration.providers.MinecraftProvider;
+import net.fabricmc.loom.configuration.providers.forge.FieldMigratedMappingsProvider;
import net.fabricmc.loom.configuration.providers.forge.ForgeProvider;
import net.fabricmc.loom.configuration.providers.forge.ForgeUniversalProvider;
import net.fabricmc.loom.configuration.providers.forge.ForgeUserdevProvider;
@@ -387,7 +388,7 @@ public class LoomGradleExtension {
}
public MappingsProvider getMappingsProvider() {
- return getDependencyManager().getProvider(MappingsProvider.class);
+ return getDependencyManager().getProvider(isForge() ? FieldMigratedMappingsProvider.class : MappingsProvider.class);
}
public McpConfigProvider getMcpConfigProvider() {
diff --git a/src/main/java/net/fabricmc/loom/configuration/CompileConfiguration.java b/src/main/java/net/fabricmc/loom/configuration/CompileConfiguration.java
index a3e7e448..7b31059d 100644
--- a/src/main/java/net/fabricmc/loom/configuration/CompileConfiguration.java
+++ b/src/main/java/net/fabricmc/loom/configuration/CompileConfiguration.java
@@ -40,6 +40,7 @@ import net.fabricmc.loom.build.mixin.ScalaApInvoker;
import net.fabricmc.loom.configuration.ide.SetupIntelijRunConfigs;
import net.fabricmc.loom.configuration.providers.LaunchProvider;
import net.fabricmc.loom.configuration.providers.MinecraftProvider;
+import net.fabricmc.loom.configuration.providers.forge.FieldMigratedMappingsProvider;
import net.fabricmc.loom.configuration.providers.forge.ForgeProvider;
import net.fabricmc.loom.configuration.providers.forge.ForgeUniversalProvider;
import net.fabricmc.loom.configuration.providers.forge.ForgeUserdevProvider;
@@ -173,7 +174,7 @@ public final class CompileConfiguration {
dependencyManager.addProvider(new ForgeUniversalProvider(project));
}
- dependencyManager.addProvider(new MappingsProvider(project));
+ dependencyManager.addProvider(extension.isForge() ? new FieldMigratedMappingsProvider(project) : new MappingsProvider(project));
dependencyManager.addProvider(new LaunchProvider(project));
dependencyManager.handleDependencies(project);
diff --git a/src/main/java/net/fabricmc/loom/configuration/LoomDependencyManager.java b/src/main/java/net/fabricmc/loom/configuration/LoomDependencyManager.java
index 8b97f81e..d325457b 100644
--- a/src/main/java/net/fabricmc/loom/configuration/LoomDependencyManager.java
+++ b/src/main/java/net/fabricmc/loom/configuration/LoomDependencyManager.java
@@ -72,7 +72,7 @@ public class LoomDependencyManager {
return provider;
}
- public <T> T getProvider(Class<T> clazz) {
+ public <T> T getProvider(Class<? extends T> clazz) {
for (DependencyProvider provider : dependencyProviderList) {
if (provider.getClass() == clazz) {
return (T) provider;
diff --git a/src/main/java/net/fabricmc/loom/configuration/providers/forge/FieldMigratedMappingsProvider.java b/src/main/java/net/fabricmc/loom/configuration/providers/forge/FieldMigratedMappingsProvider.java
new file mode 100644
index 00000000..44935cbb
--- /dev/null
+++ b/src/main/java/net/fabricmc/loom/configuration/providers/forge/FieldMigratedMappingsProvider.java
@@ -0,0 +1,258 @@
+package net.fabricmc.loom.configuration.providers.forge;
+
+import java.io.BufferedReader;
+import java.io.File;
+import java.io.IOException;
+import java.io.UncheckedIOException;
+import java.nio.charset.StandardCharsets;
+import java.nio.file.Files;
+import java.nio.file.Path;
+import java.nio.file.StandardOpenOption;
+import java.util.AbstractMap;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Objects;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.function.Consumer;
+
+import com.google.common.collect.HashBasedTable;
+import com.google.common.collect.Table;
+import com.google.common.reflect.TypeToken;
+import com.google.gson.Gson;
+import dev.architectury.mappingslayers.api.mutable.MappingsEntry;
+import dev.architectury.mappingslayers.api.mutable.MutableClassDef;
+import dev.architectury.mappingslayers.api.mutable.MutableFieldDef;
+import dev.architectury.mappingslayers.api.mutable.MutableTinyTree;
+import dev.architectury.mappingslayers.api.utils.MappingsUtils;
+import dev.architectury.refmapremapper.utils.DescriptorRemapper;
+import org.gradle.api.Project;
+import org.objectweb.asm.ClassReader;
+import org.objectweb.asm.ClassVisitor;
+import org.objectweb.asm.FieldVisitor;
+import org.objectweb.asm.Opcodes;
+
+import net.fabricmc.loom.LoomGradleExtension;
+import net.fabricmc.loom.LoomGradlePlugin;
+import net.fabricmc.loom.configuration.providers.mappings.MappingsProvider;
+import net.fabricmc.loom.util.FileSystemUtil;
+import net.fabricmc.loom.util.ThreadingUtils;
+import net.fabricmc.loom.util.srg.SrgMerger;
+import net.fabricmc.mapping.tree.ClassDef;
+import net.fabricmc.mapping.tree.FieldDef;
+import net.fabricmc.mapping.tree.TinyMappingFactory;
+import net.fabricmc.mapping.tree.TinyTree;
+
+public class FieldMigratedMappingsProvider extends MappingsProvider {
+ private List<Map.Entry<FieldMember, String>> migratedFields = new ArrayList<>();
+ public Path migratedFieldsCache;
+ public Path rawTinyMappings;
+ public Path rawTinyMappingsWithSrg;
+
+ public FieldMigratedMappingsProvider(Project project) {
+ super(project);
+ }
+
+ @Override
+ public void provide(DependencyInfo dependency, Consumer<Runnable> postPopulationScheduler) throws Exception {
+ LoomGradleExtension extension = getExtension();
+ PatchProvider patchProvider = getExtension().getPatchProvider();
+ migratedFieldsCache = patchProvider.getProjectCacheFolder().resolve("migrated-fields.json");
+ migratedFields.clear();
+
+ if (LoomGradlePlugin.refreshDeps) {
+ Files.deleteIfExists(migratedFieldsCache);
+ } else if (Files.exists(migratedFieldsCache)) {
+ try (BufferedReader reader = Files.newBufferedReader(migratedFieldsCache)) {
+ Map<String, String> map = new Gson().fromJson(reader, new TypeToken<Map<String, String>>() {
+ }.getType());
+ migratedFields = new ArrayList<>();
+ map.forEach((key, newDescriptor) -> {
+ String[] split = key.split("#");
+ migratedFields.add(new AbstractMap.SimpleEntry<>(new FieldMember(split[0], split[1]), newDescriptor));
+ });
+ }
+ }
+
+ super.provide(dependency, postPopulationScheduler);
+ }
+
+ @Override
+ public void manipulateMappings(Path mappingsJar) throws IOException {
+ LoomGradleExtension extension = getExtension();
+ Path mappingsFolder = mappingsDir.resolve(extension.getMinecraftProvider().getMinecraftVersion() + "/forge-" + extension.getPatchProvider().forgeVersion);
+ this.rawTinyMappings = tinyMappings.toPath();
+ this.rawTinyMappingsWithSrg = tinyMappingsWithSrg;
+ String mappingsJarName = mappingsJar.getFileName().toString();
+
+ if (getExtension().shouldGenerateSrgTiny()) {
+ if (Files.notExists(rawTinyMappingsWithSrg) || isRefreshDeps()) {
+ // Merge tiny mappings with srg
+ SrgMerger.mergeSrg(getExtension().getSrgProvider().getSrg().toPath(), rawTinyMappings, rawTinyMappingsWithSrg, true);
+ }
+ }
+
+ try {
+ Files.createDirectories(mappingsFolder);
+ } catch (IOException e) {
+ throw new UncheckedIOException(e);
+ }
+
+ tinyMappings = mappingsFolder.resolve("mappings.tiny").toFile();
+ tinyMappingsJar = mappingsFolder.resolve("mappings.jar").toFile();
+ tinyMappingsWithSrg = mappingsFolder.resolve("mappings-srg.tiny");
+ mixinTinyMappingsWithSrg = mappingsFolder.resolve("mixin-srg.tiny").toFile();
+ srgToNamedSrg = mappingsFolder.resolve("srg-to-named.srg").toFile();
+
+ try {
+ updateFieldMigration();
+ } catch (IOException e) {
+ throw new UncheckedIOException(e);
+ }
+ }
+
+ public void updateFieldMigration() throws IOException {
+ if (!Files.exists(migratedFieldsCache)) {
+ generateNewFieldMigration();
+ Map<String, String> map = new HashMap<>();
+ migratedFields.forEach(entry -> {
+ map.put(entry.getKey().owner + "#" + entry.getKey().field, entry.getValue());
+ });
+ Files.write(migratedFieldsCache, new Gson().toJson(map).getBytes(StandardCharsets.UTF_8));
+ Files.deleteIfExists(tinyMappings.toPath());
+ }
+
+ if (!Files.exists(tinyMappings.toPath())) {
+ Table<String, String, String> fieldDescriptorMap = HashBasedTable.create();
+
+ for (Map.Entry<FieldMember, String> entry : migratedFields) {
+ fieldDescriptorMap.put(entry.getKey().owner, entry.getKey().field, entry.getValue());
+ }
+
+ MutableTinyTree mappings;
+
+ try (BufferedReader reader = Files.newBufferedReader(rawTinyMappings)) {
+ mappings = MappingsUtils.copyAsMutable(TinyMappingFactory.loadWithDetection(reader));
+
+ for (MutableClassDef classDef : mappings.getClassesMutable()) {
+ Map<String, String> row = fieldDescriptorMap.row(classDef.getIntermediary());
+
+ if (!row.isEmpty()) {
+ for (MutableFieldDef fieldDef : classDef.getFieldsMutable()) {
+ String newDescriptor = row.get(fieldDef.getIntermediary());
+
+ if (newDescriptor != null) {
+ fieldDef.setDescriptor(MappingsEntry.NS_INTERMEDIARY, newDescriptor);
+ }
+ }
+ }
+ }
+ }
+
+ Files.write(tinyMappings.toPath(), MappingsUtils.serializeToString(mappings).getBytes(StandardCharsets.UTF_8), StandardOpenOption.CREATE);
+ }
+ }
+
+ private void generateNewFieldMigration() throws IOException {
+ Map<FieldMember, String> fieldDescriptorMap = new ConcurrentHashMap<>();
+ LoomGradleExtension extension = getExtension();
+ ThreadingUtils.TaskCompleter completer = ThreadingUtils.taskCompleter();
+
+ class Visitor extends ClassVisitor {
+ private final ThreadLocal<String> lastClass = new ThreadLocal<>();
+
+ Visitor(int api) {
+ super(api);
+ }
+
+ @Override
+ public void visit(int version, int access, String name, String signature, String superName, String[] interfaces) {
+ lastClass.set(name);
+ }
+
+ @Override
+ public FieldVisitor visitField(int access, String name, String descriptor, String signature, Object value) {
+ fieldDescriptorMap.put(new FieldMember(lastClass.get(), name), descriptor);
+ return super.visitField(access, name, descriptor, signature, value);
+ }
+ }
+
+ Visitor visitor = new Visitor(Opcodes.ASM9);
+
+ for (MinecraftPatchedProvider.Environment environment : MinecraftPatchedProvider.Environment.values()) {
+ File patchedSrgJar = environment.patchedSrgJar.apply(extension.getMappingsProvider().patchedProvider);
+ FileSystemUtil.FileSystemDelegate system = FileSystemUtil.getJarFileSystem(patchedSrgJar, false);
+ completer.onComplete(value -> system.close());
+
+ for (Path fsPath : (Iterable<? extends Path>) Files.walk(system.get().getPath("/"))::iterator) {
+ if (Files.isRegularFile(fsPath) && fsPath.toString().endsWith(".class")) {
+ completer.add(() -> {
+ byte[] bytes = Files.readAllBytes(fsPath);
+ new ClassReader(bytes).accept(visitor, ClassReader.SKIP_CODE | ClassReader.SKIP_DEBUG | ClassReader.SKIP_FRAMES);
+ });
+ }
+ }
+ }
+
+ completer.complete();
+ Map<FieldMember, String> migratedFields = new HashMap<>();
+
+ try (BufferedReader reader = Files.newBufferedReader(rawTinyMappingsWithSrg)) {
+ TinyTree mappings = TinyMappingFactory.loadWithDetection(reader);
+ Map<String, String> srgToIntermediary = new HashMap<>();
+
+ for (ClassDef aClass : mappings.getClasses()) {
+ srgToIntermediary.put(aClass.getName("srg"), aClass.getName("intermediary"));
+ }
+
+ for (ClassDef classDef : mappings.getClasses()) {
+ String ownerSrg = classDef.getName("srg");
+ String ownerIntermediary = classDef.getName("intermediary");
+
+ for (FieldDef fieldDef : classDef.getFields()) {
+ String fieldSrg = fieldDef.getName("srg");
+ String descriptorSrg = fieldDef.getDescriptor("srg");
+
+ FieldMember member = new FieldMember(ownerSrg, fieldSrg);
+ String newDescriptor = fieldDescriptorMap.get(member);
+
+ if (newDescriptor != null && !newDescriptor.equals(descriptorSrg)) {
+ String fieldIntermediary = fieldDef.getName("intermediary");
+ String descriptorIntermediary = fieldDef.getDescriptor("intermediary");
+ String newDescriptorRemapped = DescriptorRemapper.remapDescriptor(newDescriptor,
+ clazz -> srgToIntermediary.getOrDefault(clazz, clazz));
+ migratedFields.put(new FieldMember(ownerIntermediary, fieldIntermediary), newDescriptorRemapped);
+ getProject().getLogger().info(ownerIntermediary + "#" + fieldIntermediary + ": " + descriptorIntermediary + " -> " + newDescriptorRemapped);
+ }
+ }
+ }
+ }
+
+ this.migratedFields.clear();
+ this.migratedFields.addAll(migratedFields.entrySet());
+ }
+
+ public static class FieldMember {
+ public String owner;
+ public String field;
+
+ public FieldMember(String owner, String field) {
+ this.owner = owner;
+ this.field = field;
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) return true;
+ if (o == null || getClass() != o.getClass()) return false;
+ FieldMember that = (FieldMember) o;
+ return Objects.equals(owner, that.owner) && Objects.equals(field, that.field);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(owner, field);
+ }
+ }
+}
diff --git a/src/main/java/net/fabricmc/loom/configuration/providers/forge/MinecraftPatchedProvider.java b/src/main/java/net/fabricmc/loom/configuration/providers/forge/MinecraftPatchedProvider.java
index 170f2b65..666b8530 100644
--- a/src/main/java/net/fabricmc/loom/configuration/providers/forge/MinecraftPatchedProvider.java
+++ b/src/main/java/net/fabricmc/loom/configuration/providers/forge/MinecraftPatchedProvider.java
@@ -77,7 +77,6 @@ import org.zeroturnaround.zip.ZipUtil;
import net.fabricmc.loom.configuration.DependencyProvider;
import net.fabricmc.loom.configuration.providers.MinecraftProvider;
-import net.fabricmc.loom.configuration.providers.mappings.MappingsProvider;
import net.fabricmc.loom.configuration.providers.minecraft.MinecraftMappedProvider;
import net.fabricmc.loom.util.Checksum;
import net.fabricmc.loom.util.Constants;
@@ -92,7 +91,6 @@ import net.fabricmc.loom.util.srg.SpecialSourceExecutor;
import net.fabricmc.mapping.tree.TinyTree;
public class MinecraftPatchedProvider extends DependencyProvider {
- private final MappingsProvider mappingsProvider;
// Step 1: Remap Minecraft to SRG
private File minecraftClientSrgJar;
private File minecraftServerSrgJar;
@@ -112,9 +110,8 @@ public class MinecraftPatchedProvider extends DependencyProvider {
private File projectAt = null;
private boolean atDirty = false;
- public MinecraftPatchedProvider(MappingsProvider mappingsProvider, Project project) {
+ public MinecraftPatchedProvider(Project project) {
super(project);
- this.mappingsProvider = mappingsProvider;
}
public void initFiles() throws IOException {
@@ -149,26 +146,28 @@ public class MinecraftPatchedProvider extends DependencyProvider {
MinecraftProvider minecraftProvider = getExtension().getMinecraftProvider();
PatchProvider patchProvider = getExtension().getPatchProvider();
String minecraftVersion = minecraftProvider.getMinecraftVersion();
- String jarSuffix = "-patched-forge-" + patchProvider.forgeVersion;
+ String patchId = "forge-" + patchProvider.forgeVersion;
if (getExtension().useFabricMixin) {
- jarSuffix += "-fabric-mixin";
+ patchId += "-fabric-mixin";
}
- minecraftProvider.setJarSuffix(jarSuffix);
-
File globalCache = getExtension().getUserCache();
File cache = usesProjectCache() ? getExtension().getProjectPersistentCache() : globalCache;
+ File globalDir = new File(globalCache, patchId);
+ File projectDir = new File(cache, patchId);
+ globalDir.mkdirs();
+ projectDir.mkdirs();
minecraftClientSrgJar = new File(globalCache, "minecraft-" + minecraftVersion + "-client-srg.jar");
minecraftServerSrgJar = new File(globalCache, "minecraft-" + minecraftVersion + "-server-srg.jar");
- minecraftClientPatchedSrgJar = new File(globalCache, "minecraft-" + minecraftVersion + "-client-srg" + jarSuffix + ".jar");
- minecraftServerPatchedSrgJar = new File(globalCache, "minecraft-" + minecraftVersion + "-server-srg" + jarSuffix + ".jar");
- minecraftClientPatchedSrgATJar = new File(cache, "minecraft-" + minecraftVersion + "-client-srg-at" + jarSuffix + ".jar");
- minecraftServerPatchedSrgATJar = new File(cache, "minecraft-" + minecraftVersion + "-server-srg-at" + jarSuffix + ".jar");
- minecraftClientPatchedOfficialJar = new File(cache, "minecraft-" + minecraftVersion + "-client" + jarSuffix + ".jar");
- minecraftServerPatchedOfficialJar = new File(cache, "minecraft-" + minecraftVersion + "-server" + jarSuffix + ".jar");
- minecraftMergedPatchedJar = new File(cache, "minecraft-" + minecraftVersion + "-merged" + jarSuffix + ".jar");
+ minecraftClientPatchedSrgJar = new File(globalDir, "client-srg-patched.jar");
+ minecraftServerPatchedSrgJar = new File(globalDir, "server-srg-patched.jar");
+ minecraftClientPatchedSrgATJar = new File(projectDir, "client-srg-at-patched.jar");
+ minecraftServerPatchedSrgATJar = new File(projectDir, "server-srg-at-patched.jar");
+ minecraftClientPatchedOfficialJar = new File(projectDir, "client-patched.jar");
+ minecraftServerPatchedOfficialJar = new File(projectDir, "server-patched.jar");
+ minecraftMergedPatchedJar = new File(projectDir, "merged-patched.jar");
if (isRefreshDeps() || Stream.of(getGlobalCaches()).anyMatch(Predicates.not(File::exists))) {
cleanAllCache();
@@ -210,6 +209,8 @@ public class MinecraftPatchedProvider extends DependencyProvider {
};
}
+ private boolean dirty;
+
@Override
public void provide(DependencyInfo dependency, Consumer<Runnable> postPopulationScheduler) throws Exception {
initFiles();
@@ -218,22 +219,24 @@ public class MinecraftPatchedProvider extends DependencyProvider {
getProject().getLogger().lifecycle(":found dirty access transformers");
}
- boolean dirty = false;
+ this.dirty = false;
if (!minecraftClientSrgJar.exists() || !minecraftServerSrgJar.exists()) {
- dirty = true;
+ this.dirty = true;
// Remap official jars to MCPConfig remapped srg jars
createSrgJars(getProject().getLogger());
}
if (!minecraftClientPatchedSrgJar.exists() || !minecraftServerPatchedSrgJar.exists()) {
- dirty = true;
+ this.dirty = true;
patchJars(getProject().getLogger());
injectForgeClasses(getProject().getLogger());
}
+ }
+ public void finishProvide() throws Exception {
if (atDirty || !minecraftClientPatchedSrgATJar.exists() || !minecraftServerPatchedSrgATJar.exists()) {
- dirty = true;
+ this.dirty = true;
accessTransformForge(getProject().getLogger());
}
@@ -244,6 +247,8 @@ public class MinecraftPatchedProvider extends DependencyProvider {
if (dirty || !minecraftMergedPatchedJar.exists()) {
mergeJars(getProject().getLogger());
}
+
+ this.dirty = false;
}
private void writeAtHash() throws IOException {
@@ -285,9 +290,9 @@ public class MinecraftPatchedProvider extends DependencyProvider {
DownloadUtil.downloadIfChanged(new URL("https://repo1.maven.org/maven2/net/md-5/SpecialSource/1.8.3/SpecialSource-1.8.3-shaded.jar"), specialSourceJar, getProject().getLogger(), true);
ThreadingUtils.run(() -> {
- Files.copy(SpecialSourceExecutor.produceSrgJar(getProject(), mappingsProvider, "client", specialSourceJar, minecraftProvider.minecraftClientJar.toPath(), tmpSrg[0]), minecraftClientSrgJar.toPath());
+ Files.copy(SpecialSourceExecutor.produceSrgJar(getProject(), "client", specialSourceJar, minecraftProvider.minecraftClientJar.toPath(), tmpSrg[0]), minecraftClientSrgJar.toPath());
}, () -> {
- Files.copy(SpecialSourceExecutor.produceSrgJar(getProject(), mappingsProvider, "server", specialSourceJar, minecraftProvider.minecraftServerJar.toPath(), tmpSrg[0]), minecraftServerSrgJar.toPath());
+ Files.copy(SpecialSourceExecutor.produceSrgJar(getProject(), "server", specialSourceJar, minecraftProvider.minecraftServerJar.toPath(), tmpSrg[0]), minecraftServerSrgJar.toPath());
});
}
@@ -327,7 +332,7 @@ public class MinecraftPatchedProvider extends DependencyProvider {
private void injectForgeClasses(Logger logger) throws IOException {
logger.lifecycle(":injecting forge classes into minecraft");
- ThreadingUtils.run(Arrays.asList(Environment.values()), environment -> {
+ ThreadingUtils.run(Environment.values(), environment -> {
copyAll(getExtension().getForgeUniversalProvider().getForge(), environment.patchedSrgJar.apply(this));
copyUserdevFiles(getExtension().getForgeUserdevProvider().getUserdevJar(), environment.patchedSrgJar.apply(this));
});
@@ -392,7 +397,7 @@ public class MinecraftPatchedProvider extends DependencyProvider {
((Map<?, ?>) field.get(list)).clear();
}
- private enum Environment {
+ public enum Environment {
CLIENT(provider -> provider.minecraftClientSrgJar,
provider -> provider.minecraftClientPatchedSrgJar,
provider -> provider.minecraftClientPatchedSrgATJar,
@@ -427,7 +432,7 @@ public class MinecraftPatchedProvider extends DependencyProvider {
private void remapPatchedJars(Logger logger) throws Exception {
Path[] libraries = MinecraftMappedProvider.getRemapClasspath(getProject());
- ThreadingUtils.run(Arrays.asList(Environment.values()), environment -> {
+ ThreadingUtils.run(Environment.values(), environment -> {
logger.lifecycle(":remapping minecraft (TinyRemapper, " + environment.side() + ", srg -> official)");
TinyTree mappingsWithSrg = getExtension().getMappingsProvider().getMappingsWithSrg();
@@ -464,7 +469,7 @@ public class MinecraftPatchedProvider extends DependencyProvider {
patchJars(minecraftClientSrgJar, minecraftClientPatchedSrgJar, patchProvider.clientPatches);
patchJars(minecraftServerSrgJar, minecraftServerPatchedSrgJar, patchProvider.serverPatches);
- ThreadingUtils.run(Arrays.asList(Environment.values()), environment -> {
+ ThreadingUtils.run(Environment.values(), environment -> {
copyMissingClasses(environment.srgJar.apply(this), environment.patchedSrgJar.apply(this));
fixParameterAnnotation(environment.patchedSrgJar.apply(this));
});
@@ -474,7 +479,7 @@ public class MinecraftPatchedProvider extends DependencyProvider {
PrintStream previous = System.out;
try {
- System.setOut(new PrintStream(new NullOutputStream()));
+ System.setOut(new PrintStream(NullOutputStream.NULL_OUTPUT_STREAM));
} catch (SecurityException ignored) {
// Failed to replace logger filter, just ignore
}
@@ -507,7 +512,7 @@ public class MinecraftPatchedProvider extends DependencyProvider {
private void walkFileSystems(File source, File target, Predicate<Path> filter, Function<FileSystem, Iterable<Path>> toWalk, FsPathConsumer action)
throws IOException {
try (FileSystemUtil.FileSystemDelegate sourceFs = FileSystemUtil.getJarFileSystem(source, false);
- FileSystemUtil.FileSystemDelegate targetFs = FileSystemUtil.getJarFileSystem(target, false)) {
+ FileSystemUtil.FileSystemDelegate targetFs = FileSystemUtil.getJarFileSystem(target, false)) {
for (Path sourceDir : toWalk.apply(sourceFs.get())) {
Path dir = sourceDir.toAbsolutePath();
Files.walk(dir)
diff --git a/src/main/java/net/fabricmc/loom/configuration/providers/forge/PatchProvider.java b/src/main/java/net/fabricmc/loom/configuration/providers/forge/PatchProvider.java
index 24f1c866..b9924a16 100644
--- a/src/main/java/net/fabricmc/loom/configuration/providers/forge/PatchProvider.java
+++ b/src/main/java/net/fabricmc/loom/configuration/providers/forge/PatchProvider.java
@@ -24,6 +24,8 @@
package net.fabricmc.loom.configuration.providers.forge;
+import java.io.IOException;
+import java.io.UncheckedIOException;
import java.net.URI;
import java.nio.file.FileSystem;
import java.nio.file.FileSystems;
@@ -42,6 +44,7 @@ public class PatchProvider extends DependencyProvider {
public Path clientPatches;
public Path serverPatches;
public String forgeVersion;
+ public Path projectCacheFolder;
public PatchProvider(Project project) {
super(project);
@@ -65,8 +68,19 @@ public class PatchProvider extends DependencyProvider {
private void init(String forgeVersion) {
this.forgeVersion = forgeVersion;
- clientPatches = getExtension().getProjectPersistentCache().toPath().resolve("patches-" + forgeVersion + "-client.lzma");
- serverPatches = getExtension().getProjectPersistentCache().toPath().resolve("patches-" + forgeVersion + "-server.lzma");
+ projectCacheFolder = getExtension().getProjectPersistentCache().toPath().resolve(forgeVersion);
+ clientPatches = projectCacheFolder.resolve("patches-client.lzma");
+ serverPatches = projectCacheFolder.resolve("patches-server.lzma");
+
+ try {
+ Files.createDirectories(projectCacheFolder);
+ } catch (IOException e) {
+ throw new UncheckedIOException(e);
+ }
+ }
+
+ public Path getProjectCacheFolder() {
+ return projectCacheFolder;
}
@Override
diff --git a/src/main/java/net/fabricmc/loom/configuration/providers/mappings/MappingsProvider.java b/src/main/java/net/fabricmc/loom/configuration/providers/mappings/MappingsProvider.java
index c7160bea..632515df 100644
--- a/src/main/java/net/fabricmc/loom/configuration/providers/mappings/MappingsProvider.java
+++ b/src/main/java/net/fabricmc/loom/configuration/providers/mappings/MappingsProvider.java
@@ -86,7 +86,7 @@ public class MappingsProvider extends DependencyProvider {
public String minecraftVersion;
public String mappingsVersion;
- private final Path mappingsDir;
+ protected final Path mappingsDir;
private final Path mappingsStepsDir;
private Path intermediaryTiny;
private boolean hasRefreshed = false;
@@ -94,8 +94,8 @@ public class MappingsProvider extends DependencyProvider {
private Path baseTinyMappings;
// The mappings we use in practice
public File tinyMappings;
+ // tinyMappings wrapped in a jar
public File tinyMappingsJar;
- public File mappingsMixinExport;
public Path tinyMappingsWithSrg;
public File mixinTinyMappingsWithSrg; // FORGE: The mixin mappings have srg names in intermediary.
public File srgToNamedSrg; // FORGE: srg to named in srg file format
@@ -181,12 +181,13 @@ public class MappingsProvider extends DependencyProvider {
jarClassifier = jarClassifier + depStringSplit[3];
}
- tinyMappings = mappingsDir.resolve(StringUtils.removeSuffix(mappingsJar.getName(), ".jar") + ".tiny").toFile();
- unpickDefinitionsFile = mappingsDir.resolve(StringUtils.removeSuffix(mappingsJar.getName(), ".jar") + ".unpick").toFile();
- tinyMappingsJar = new File(getExtension().getUserCache(), mappingsJar.getName().replace(".jar", "-" + jarClassifier + ".jar"));
- tinyMappingsWithSrg = mappingsDir.resolve(StringUtils.removeSuffix(mappingsJar.getName(), ".jar") + "-srg.tiny");
- mixinTinyMappingsWithSrg = mappingsDir.resolve(StringUtils.removeSuffix(mappingsJar.getName(), ".jar") + "-mixin-srg.tiny").toFile();
- srgToNamedSrg = mappingsDir.resolve(StringUtils.removeSuffix(mappingsJar.getName(), ".jar") + "-srg-named.srg").toFile();
+ String removeSuffix = StringUtils.removeSuffix(mappingsJar.getName(), ".jar");
+ tinyMappings = mappingsDir.resolve(removeSuffix + ".tiny").toFile();
+ unpickDefinitionsFile = mappingsDir.resolve(removeSuffix + ".unpick").toFile();
+ tinyMappingsJar = new File(getExtension().getUserCache(), removeSuffix + "-" + jarClassifier + ".jar");
+ tinyMappingsWithSrg = mappingsDir.resolve(removeSuffix + "-srg.tiny");
+ mixinTinyMappingsWithSrg = mappingsDir.resolve(removeSuffix + "-mixin-srg.tiny").toFile();
+ srgToNamedSrg = mappingsDir.resolve(removeSuffix + "-srg-named.srg").toFile();
if (!tinyMappings.exists() || isRefreshDeps()) {
storeMappings(getProject(), minecraftProvider, mappingsJar.toPath(), postPopulationScheduler);
@@ -196,6 +197,20 @@ public class MappingsProvider extends DependencyProvider {
}
}
+ if (getExtension().isForge()) {
+ patchedProvider = new MinecraftPatchedProvider(getProject());
+ patchedProvider.provide(dependency, postPopulationScheduler);
+ }
+
+ manipulateMappings(mappingsJar.toPath());
+
+ if (getExtension().shouldGenerateSrgTiny()) {
+ if (Files.notExists(tinyMappingsWithSrg) || isRefreshDeps()) {
+ // Merge tiny mappings with srg
+ SrgMerger.mergeSrg(getExtension().getSrgProvider().getSrg().toPath(), tinyMappings.toPath(), tinyMappingsWithSrg, true);
+ }
+ }
+
if (!tinyMappingsJar.exists() || isRefreshDeps()) {
ZipUtil.pack(new ZipEntrySource[] {new FileSource("mappings/mappings.tiny", tinyMappings)}, tinyMappingsJar);
}
@@ -211,12 +226,6 @@ public class MappingsProvider extends DependencyProvider {
populateUnpickClasspath();
}
- if (getExtension().shouldGenerateSrgTiny()) {
- if (Files.notExists(tinyMappingsWithSrg) || isRefreshDeps()) {
- SrgMerger.mergeSrg(getExtension().getSrgProvider().getSrg().toPath(), tinyMappings.toPath(), tinyMappingsWithSrg, true);
- }
- }
-
if (getExtension().isForge()) {
if (!getExtension().shouldGenerateSrgTiny()) {
throw new IllegalStateException("We have to generate srg tiny in a forge environment!");
@@ -247,8 +256,7 @@ public class MappingsProvider extends DependencyProvider {
processorManager.setupProcessors();
if (extension.isForge()) {
- patchedProvider = new MinecraftPatchedProvider(this, getProject());
- patchedProvider.provide(dependency, postPopulationScheduler);
+ patchedProvider.finishProvide();
}
if (processorManager.active() || (extension.isForge() && patchedProvider.usesProjectCache())) {
@@ -262,6 +270,8 @@ public class MappingsProvider extends DependencyProvider {
mappedProvider.provide(dependency, postPopulationScheduler);
}
+ public void manipulateMappings(Path mappingsJar) throws IOException { }
+
private void storeMappings(Project project, MinecraftProvider minecraftProvider, Path yarnJar, Consumer<Runnable> postPopulationScheduler)
throws Exception {
project.getLogger().info(":extracting " + yarnJar.getFileName());
diff --git a/src/main/java/net/fabricmc/loom/util/ThreadingUtils.java b/src/main/java/net/fabricmc/loom/util/ThreadingUtils.java
index e61a297c..0645f319 100644
--- a/src/main/java/net/fabricmc/loom/util/ThreadingUtils.java
+++ b/src/main/java/net/fabricmc/loom/util/ThreadingUtils.java
@@ -40,6 +40,12 @@ import java.util.stream.Collectors;
import com.google.common.base.Stopwatch;
public class ThreadingUtils {
+ public static <T> void run(T[] values, UnsafeConsumer<T> action) {
+ run(Arrays.stream(values)
+ .<UnsafeRunnable>map(t -> () -> action.accept(t))
+ .collect(Collectors.toList()));
+ }
+
public static <T> void run(Collection<T> values, UnsafeConsumer<T> action) {
run(values.stream()
.<UnsafeRunnable>map(t -> () -> action.accept(t))
diff --git a/src/main/java/net/fabricmc/loom/util/srg/SpecialSourceExecutor.java b/src/main/java/net/fabricmc/loom/util/srg/SpecialSourceExecutor.java
index 72a482cf..1da2266d 100644
--- a/src/main/java/net/fabricmc/loom/util/srg/SpecialSourceExecutor.java
+++ b/src/main/java/net/fabricmc/loom/util/srg/SpecialSourceExecutor.java
@@ -43,7 +43,7 @@ import net.fabricmc.loom.LoomGradleExtension;
import net.fabricmc.loom.configuration.providers.mappings.MappingsProvider;
public class SpecialSourceExecutor {
- public static Path produceSrgJar(Project project, MappingsProvider provider, String side, File specialSourceJar, Path officialJar, Path srgPath)
+ public static Path produceSrgJar(Project project, String side, File specialSourceJar, Path officialJar, Path srgPath)
throws Exception {
Set<String> filter = Files.readAllLines(srgPath, StandardCharsets.UTF_8).stream()
.filter(s -> !s.startsWith("\t"))