diff --git a/build.gradle b/build.gradle index 163d1818e4..7406db8017 100644 --- a/build.gradle +++ b/build.gradle @@ -165,7 +165,7 @@ dependencies { implementation libs.night.config.toml // Legacy Forge patches - implementation libs.lzma + implementation libs.xz // Testing testImplementation(gradleTestKit()) diff --git a/gradle/libs.versions.toml b/gradle/libs.versions.toml index af191eda4e..ea4aa3c137 100644 --- a/gradle/libs.versions.toml +++ b/gradle/libs.versions.toml @@ -28,7 +28,7 @@ forge-diffpatch = "2.0.7" night-config = "3.6.6" datafixerupper = "6.0.8" at = "1.0.1" -lzma = "1.3" +xz = "1.8" [libraries] # Loom compile libraries @@ -63,7 +63,7 @@ forge-diffpatch = { module = "net.minecraftforge:DiffPatch", version.ref = "forg night-config-toml = { module = "com.electronwill.night-config:toml", version.ref = "night-config" } datafixerupper = { module = "com.mojang:datafixerupper", version.ref = "datafixerupper" } at = { module = "dev.architectury:at", version.ref = "at" } -lzma = { module = "com.github.jponge:lzma-java", version.ref = "lzma" } +xz = { module = "org.tukaani:xz", version.ref = "xz" } [plugins] kotlin = { id = "org.jetbrains.kotlin.jvm", version.ref = "kotlin" } diff --git a/src/main/java/net/fabricmc/loom/LoomGradleExtension.java b/src/main/java/net/fabricmc/loom/LoomGradleExtension.java index 24f1852b3c..064a1252b8 100644 --- a/src/main/java/net/fabricmc/loom/LoomGradleExtension.java +++ b/src/main/java/net/fabricmc/loom/LoomGradleExtension.java @@ -178,8 +178,12 @@ default boolean isForgeLikeAndNotOfficial() { return isForgeLike() && !getMcpConfigProvider().isOfficial(); } + default int getForgeSpec() { + return getForgeUserdevProvider().getForgeSpec(); + } + default boolean isLegacyForge() { - return isForge() && getForgeUserdevProvider().isLegacyForge(); + return isForge() && getForgeSpec() <= 1; } default boolean isModernForge() { diff --git a/src/main/java/net/fabricmc/loom/configuration/CompileConfiguration.java b/src/main/java/net/fabricmc/loom/configuration/CompileConfiguration.java index cb0f47c3ca..db4250c165 100644 --- a/src/main/java/net/fabricmc/loom/configuration/CompileConfiguration.java +++ b/src/main/java/net/fabricmc/loom/configuration/CompileConfiguration.java @@ -227,13 +227,13 @@ private synchronized void setupMinecraft(ConfigContext configContext) throws Exc // but before MinecraftPatchedProvider.provide. setupDependencyProviders(project, extension); - if (extension.isLegacyForge()) { + if (extension.getForgeSpec() <= 2) { extension.setIntermediateMappingsProvider(GeneratedIntermediateMappingsProvider.class, provider -> { provider.minecraftProvider = minecraftProvider; }); } - if (extension.isForgeLike() && !extension.isLegacyForge()) { + if (extension.isForgeLike() && extension.getForgeSpec() > 2) { // Excluded on legacy forge because it pulls in a log4j-api version newer than what forge wants and we don't // need it anyway project.getDependencies().add(Configurations.FORGE_EXTRA, LoomVersions.UNPROTECT.mavenNotation()); diff --git a/src/main/java/net/fabricmc/loom/configuration/providers/forge/ForgeMigratedMappingConfiguration.java b/src/main/java/net/fabricmc/loom/configuration/providers/forge/ForgeMigratedMappingConfiguration.java index ee4c568bee..1c0bcd6f66 100644 --- a/src/main/java/net/fabricmc/loom/configuration/providers/forge/ForgeMigratedMappingConfiguration.java +++ b/src/main/java/net/fabricmc/loom/configuration/providers/forge/ForgeMigratedMappingConfiguration.java @@ -53,7 +53,7 @@ public ForgeMigratedMappingConfiguration(String mappingsIdentifier, Path mapping protected void manipulateMappings(Project project, Path mappingsJar) throws IOException { LoomGradleExtension extension = LoomGradleExtension.get(project); - if (extension.isLegacyForge()) { + if (extension.getForgeSpec() <= 2) { // Legacy forge patches are in official namespace, so if the type of a field is changed by them, then that // is effectively a new field and not traceable to any mapping. Therefore this does not apply to it. return; diff --git a/src/main/java/net/fabricmc/loom/configuration/providers/forge/ForgeUserdevProvider.java b/src/main/java/net/fabricmc/loom/configuration/providers/forge/ForgeUserdevProvider.java index e6ac6dc61a..02b18b1a21 100644 --- a/src/main/java/net/fabricmc/loom/configuration/providers/forge/ForgeUserdevProvider.java +++ b/src/main/java/net/fabricmc/loom/configuration/providers/forge/ForgeUserdevProvider.java @@ -53,7 +53,7 @@ public class ForgeUserdevProvider extends DependencyProvider { private JsonObject json; private UserdevConfig config; Path joinedPatches; - private Boolean isLegacyForge; + private Integer forgeSpec; public ForgeUserdevProvider(Project project) { super(project); @@ -88,10 +88,13 @@ public void provide(DependencyInfo dependency) throws Exception { try (Reader reader = Files.newBufferedReader(configJson)) { json = new Gson().fromJson(reader, JsonObject.class); - isLegacyForge = !json.has("mcp"); + // Some Forge versions for 1.13.2 specify mcp, but have spec=1. We just "hack" this here. + forgeSpec = json.has("mcp") ? Math.max(2, json.get("spec").getAsInt()) : 1; - if (isLegacyForge) { + if (forgeSpec <= 1) { json = createManifestFromForgeGradle2(dependency, json); + } else if (forgeSpec <= 2) { + addLegacyMCPRepo(); } config = UserdevConfig.CODEC.parse(JsonOps.INSTANCE, json) @@ -106,7 +109,7 @@ public void provide(DependencyInfo dependency) throws Exception { addDependency(config.universal(), Constants.Configurations.FORGE_UNIVERSAL); - if (!isLegacyForge && Files.notExists(joinedPatches)) { + if (forgeSpec >= 2 && Files.notExists(joinedPatches)) { Files.write(joinedPatches, ZipUtils.unpack(userdevJar.toPath(), config.binpatches())); } } @@ -177,6 +180,10 @@ private static JsonObject createLegacyRuns() { private static JsonArray createLegacyAts() { JsonArray array = new JsonArray(); array.add("merged_at.cfg"); + array.add("forge_at.cfg"); + array.add("fml_at.cfg"); + array.add("src/main/resources/forge_at.cfg"); + array.add("src/main/resources/fml_at.cfg"); return array; } @@ -217,12 +224,12 @@ private void addLegacyMCPRepo() { }); } - public boolean isLegacyForge() { - if (isLegacyForge == null) { + public int getForgeSpec() { + if (forgeSpec == null) { throw new IllegalArgumentException("Not yet resolved."); } - return isLegacyForge; + return forgeSpec; } public File getUserdevJar() { 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 313709a551..043c6b7573 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 @@ -43,12 +43,11 @@ import java.util.jar.JarOutputStream; import java.util.zip.ZipEntry; -import lzma.sdk.lzma.Decoder; -import lzma.sdk.lzma.Encoder; -import lzma.streams.LzmaInputStream; -import lzma.streams.LzmaOutputStream; import org.apache.commons.io.IOUtils; import org.gradle.api.Project; +import org.tukaani.xz.LZMA2Options; +import org.tukaani.xz.LZMAInputStream; +import org.tukaani.xz.LZMAOutputStream; import net.fabricmc.loom.configuration.DependencyInfo; import net.fabricmc.loom.configuration.providers.forge.fg2.Pack200Provider; @@ -100,11 +99,11 @@ private void init() { private void splitAndConvertLegacyPatches(Path joinedLegacyPatches) throws IOException { try (JarInputStream in = new JarInputStream(new ByteArrayInputStream(unpack200Lzma(joinedLegacyPatches))); OutputStream clientFileOut = Files.newOutputStream(clientPatches, CREATE, TRUNCATE_EXISTING); - LzmaOutputStream clientLzmaOut = new LzmaOutputStream(clientFileOut, new Encoder()); + LZMAOutputStream clientLzmaOut = new LZMAOutputStream(clientFileOut, new LZMA2Options(), -1); JarOutputStream clientJarOut = new JarOutputStream(clientLzmaOut); OutputStream serverFileOut = Files.newOutputStream(serverPatches, CREATE, TRUNCATE_EXISTING); - LzmaOutputStream serverLzmaOut = new LzmaOutputStream(serverFileOut, new Encoder()); - JarOutputStream serverJarOut = new JarOutputStream(serverLzmaOut); + LZMAOutputStream serverLzmaOut = new LZMAOutputStream(serverFileOut, new LZMA2Options(), -1); + JarOutputStream serverJarOut = new JarOutputStream(serverLzmaOut) ) { for (JarEntry entry; (entry = in.getNextJarEntry()) != null;) { String name = entry.getName(); @@ -153,7 +152,7 @@ private byte[] unpack200(InputStream in) throws IOException { } private byte[] unpack200Lzma(InputStream in) throws IOException { - try (LzmaInputStream lzmaIn = new LzmaInputStream(in, new Decoder())) { + try (LZMAInputStream lzmaIn = new LZMAInputStream(in)) { return unpack200(lzmaIn); } } diff --git a/src/main/java/net/fabricmc/loom/configuration/providers/mappings/MappingConfiguration.java b/src/main/java/net/fabricmc/loom/configuration/providers/mappings/MappingConfiguration.java index f848151233..61673aaaca 100644 --- a/src/main/java/net/fabricmc/loom/configuration/providers/mappings/MappingConfiguration.java +++ b/src/main/java/net/fabricmc/loom/configuration/providers/mappings/MappingConfiguration.java @@ -319,7 +319,7 @@ private static void mergeSrg(Project project, Path source, Path target) throws I LoomGradleExtension extension = LoomGradleExtension.get(project); // FIXME why is this special case necessary? - ForgeMappingsMerger.ExtraMappings extraMappings = extension.isLegacyForge() + ForgeMappingsMerger.ExtraMappings extraMappings = extension.getForgeSpec() <= 2 ? null : ForgeMappingsMerger.ExtraMappings.ofMojmapTsrg(getMojmapSrgFileIfPossible(project)); @@ -419,7 +419,8 @@ private void readAndMergeMCP(Project project, ServiceFactory serviceFactory, Min private boolean isMCP(Path path) throws IOException { try (FileSystemUtil.Delegate fs = FileSystemUtil.getJarFileSystem(path, false)) { - return Files.exists(fs.getPath("fields.csv")) && Files.exists(fs.getPath("methods.csv")); + return Files.exists(fs.getPath("fields.csv")) && Files.exists(fs.getPath("methods.csv")) + || (Files.exists(fs.getPath("conf/fields.csv")) && Files.exists(fs.getPath("conf/methods.csv"))); } } diff --git a/src/main/java/net/fabricmc/loom/decompilers/cache/ClassEntry.java b/src/main/java/net/fabricmc/loom/decompilers/cache/ClassEntry.java index 4fe53faa70..64cbf8d67e 100644 --- a/src/main/java/net/fabricmc/loom/decompilers/cache/ClassEntry.java +++ b/src/main/java/net/fabricmc/loom/decompilers/cache/ClassEntry.java @@ -50,9 +50,10 @@ public record ClassEntry(String name, List innerClasses, List su throw new IllegalArgumentException("Class name must end with '.class': " + name); } - if (!name.contains("/")) { - throw new IllegalArgumentException("Class name must be in a package: " + name); - } + // breaks in some 1.7.10 classes: + // if (!name.contains("/")) { + // throw new IllegalArgumentException("Class name must be in a package: " + name); + // } String className = name.replace(".class", ""); diff --git a/src/main/java/net/fabricmc/loom/util/srg/MCPReader.java b/src/main/java/net/fabricmc/loom/util/srg/MCPReader.java index 19d576c11f..cd55ab16ab 100644 --- a/src/main/java/net/fabricmc/loom/util/srg/MCPReader.java +++ b/src/main/java/net/fabricmc/loom/util/srg/MCPReader.java @@ -194,8 +194,11 @@ private void injectMcp(Path mcpJar, Map intermediaryToSrgMap, Ma try (FileSystemUtil.Delegate fs = FileSystemUtil.getJarFileSystem(mcpJar, false)) { Path fields = fs.getPath("fields.csv"); + if (!Files.exists(fields)) fields = fs.getPath("conf/fields.csv"); Path methods = fs.getPath("methods.csv"); + if (!Files.exists(methods)) methods = fs.getPath("conf/methods.csv"); Path params = fs.getPath("params.csv"); + if (!Files.exists(params)) params = fs.getPath("conf/params.csv"); Pattern paramsPattern = Pattern.compile("p_[^\\d]*(\\d+)_(\\d)+_?"); try (CSVReader reader = new CSVReader(Files.newBufferedReader(fields, StandardCharsets.UTF_8))) { diff --git a/src/test/groovy/net/fabricmc/loom/test/integration/forge/ForgeTest.groovy b/src/test/groovy/net/fabricmc/loom/test/integration/forge/ForgeTest.groovy index 170c93d232..43e566e0fa 100644 --- a/src/test/groovy/net/fabricmc/loom/test/integration/forge/ForgeTest.groovy +++ b/src/test/groovy/net/fabricmc/loom/test/integration/forge/ForgeTest.groovy @@ -65,6 +65,7 @@ class ForgeTest extends Specification implements GradleProjectTestTrait { '1.16.5' | '36.2.4' | '8' | '"de.oceanlabs.mcp:mcp_snapshot:20210309-1.16.5"' '1.14.4' | "28.2.23" | '8' | "loom.officialMojangMappings()" '1.14.4' | "28.2.23" | '8' | '"net.fabricmc:yarn:1.14.4+build.18:v2"' + '1.13.2' | "25.0.223" | '8' | '"de.oceanlabs.mcp:mcp_stable:47-1.13.2"' '1.12.2' | "14.23.0.2486" | '8' | '"de.oceanlabs.mcp:mcp_snapshot:20170615-1.12"' '1.8.9' | "11.15.1.2318-1.8.9" | '8' | '"de.oceanlabs.mcp:mcp_stable:22-1.8.9"' }