diff --git a/gradle.properties b/gradle.properties
index c478d5de3..7b435644f 100644
--- a/gradle.properties
+++ b/gradle.properties
@@ -5,13 +5,13 @@ group = org.quiltmc
description = The mod loading component of Quilt
url = https://github.com/quiltmc/quilt-loader
# Don't forget to change this in QuiltLoaderImpl as well
-quilt_loader = 0.26.4-beta.1
+quilt_loader = 0.26.4
# Fabric & Quilt Libraries
asm = 9.6
-sponge_mixin = 0.13.3+mixin.0.8.5
+sponge_mixin = 0.15.3+mixin.0.8.7
tiny_mappings_parser = 0.3.0+build.17
-tiny_remapper = 0.10.3
+tiny_remapper = 0.10.4
access_widener = 2.1.0
mapping_io = 0.6.1
quilt_json5 = 1.0.4+final
@@ -27,4 +27,4 @@ annotations = 24.0.1
junit_bom = 5.9.3
github_api = 1.315
flexver = 1.1.0
-mixin_extras = 0.3.5
+mixin_extras = 0.4.1
diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties
index 48c0a02ca..19cfad969 100644
--- a/gradle/wrapper/gradle-wrapper.properties
+++ b/gradle/wrapper/gradle-wrapper.properties
@@ -1,5 +1,5 @@
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
-distributionUrl=https\://services.gradle.org/distributions/gradle-8.7-bin.zip
+distributionUrl=https\://services.gradle.org/distributions/gradle-8.9-bin.zip
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists
diff --git a/minecraft/src/main/java/org/quiltmc/loader/impl/game/minecraft/BundlerClassPathCapture.java b/minecraft/src/main/java/org/quiltmc/loader/impl/game/minecraft/BundlerClassPathCapture.java
index 2e67225fc..4c7ec3caf 100644
--- a/minecraft/src/main/java/org/quiltmc/loader/impl/game/minecraft/BundlerClassPathCapture.java
+++ b/minecraft/src/main/java/org/quiltmc/loader/impl/game/minecraft/BundlerClassPathCapture.java
@@ -16,8 +16,11 @@
package org.quiltmc.loader.impl.game.minecraft;
+import java.io.IOException;
+import java.net.JarURLConnection;
import java.net.URL;
import java.net.URLClassLoader;
+import java.net.URLConnection;
import java.util.concurrent.CompletableFuture;
public final class BundlerClassPathCapture {
@@ -26,9 +29,42 @@ public final class BundlerClassPathCapture {
public static void main(String[] args) { // invoked by the bundler on a thread
try {
URLClassLoader cl = (URLClassLoader) Thread.currentThread().getContextClassLoader();
- FUTURE.complete(cl.getURLs());
+ URL[] urls = cl.getURLs();
+
+ // suppress asm library since it conflicts with Loader's, needed for MC 24w33a
+
+ URL asmUrl = cl.findResource("org/objectweb/asm/ClassReader.class");
+
+ if (asmUrl != null && (asmUrl = getJarUrl(asmUrl)) != null) {
+ for (int i = 0; i < urls.length; i++) {
+ if (urls[i].equals(asmUrl)) {
+ URL[] newUrls = new URL[urls.length - 1];
+ System.arraycopy(urls, 0, newUrls, 0, i);
+ System.arraycopy(urls, i + 1, newUrls, i, urls.length - i - 1);
+ urls = newUrls;
+ break;
+ }
+ }
+ }
+
+ FUTURE.complete(urls);
} catch (Throwable t) {
FUTURE.completeExceptionally(t);
}
}
+
+ /**
+ * Transform jar:file url to its outer file url.
+ *
+ *
jar:file:/path/to.jar!/pkg/Cls.class -> file:/path/to.jar
+ */
+ private static URL getJarUrl(URL url) throws IOException {
+ URLConnection connection = url.openConnection();
+
+ if (connection instanceof JarURLConnection) {
+ return ((JarURLConnection) connection).getJarFileURL();
+ }
+
+ return null;
+ }
}
diff --git a/minecraft/src/main/java/org/quiltmc/loader/impl/game/minecraft/McVersionLookup.java b/minecraft/src/main/java/org/quiltmc/loader/impl/game/minecraft/McVersionLookup.java
index 8f5c9510b..185e4148f 100644
--- a/minecraft/src/main/java/org/quiltmc/loader/impl/game/minecraft/McVersionLookup.java
+++ b/minecraft/src/main/java/org/quiltmc/loader/impl/game/minecraft/McVersionLookup.java
@@ -284,7 +284,9 @@ protected static String getRelease(String version) {
int year = Integer.parseInt(matcher.group(1));
int week = Integer.parseInt(matcher.group(2));
- if (year >= 24 && week >= 18) {
+ if (year >= 24 && week >= 33) {
+ return "1.21.2";
+ } else if (year == 24 && week >= 18 && week <= 21) {
return "1.21";
} else if (year == 23 && week >= 51 || year == 24 && week <= 14) {
return "1.20.5";
diff --git a/src/fabric/api/java/net/fabricmc/loader/api/entrypoint/EntrypointContainer.java b/src/fabric/api/java/net/fabricmc/loader/api/entrypoint/EntrypointContainer.java
index 9a6c3c9fe..d1aa33aee 100644
--- a/src/fabric/api/java/net/fabricmc/loader/api/entrypoint/EntrypointContainer.java
+++ b/src/fabric/api/java/net/fabricmc/loader/api/entrypoint/EntrypointContainer.java
@@ -36,4 +36,11 @@ public interface EntrypointContainer {
* Returns the mod that provided this entrypoint.
*/
ModContainer getProvider();
+
+ /**
+ * Returns a string representation of the entrypoint's definition.
+ */
+ default String getDefinition() {
+ return "";
+ }
}
diff --git a/src/fabric/impl/java/net/fabricmc/loader/impl/entrypoint/EntrypointContainerImpl.java b/src/fabric/impl/java/net/fabricmc/loader/impl/entrypoint/EntrypointContainerImpl.java
index 58ac00f1b..07a42d5a1 100644
--- a/src/fabric/impl/java/net/fabricmc/loader/impl/entrypoint/EntrypointContainerImpl.java
+++ b/src/fabric/impl/java/net/fabricmc/loader/impl/entrypoint/EntrypointContainerImpl.java
@@ -38,4 +38,9 @@ public T getEntrypoint() {
public ModContainer getProvider() {
return new ModContainerImpl(quilt.getProvider());
}
+
+ @Override
+ public String getDefinition() {
+ return quilt.getDefinition();
+ }
}
diff --git a/src/main/java/org/quiltmc/loader/api/entrypoint/EntrypointContainer.java b/src/main/java/org/quiltmc/loader/api/entrypoint/EntrypointContainer.java
index 9252ba45d..2dacf897b 100644
--- a/src/main/java/org/quiltmc/loader/api/entrypoint/EntrypointContainer.java
+++ b/src/main/java/org/quiltmc/loader/api/entrypoint/EntrypointContainer.java
@@ -35,4 +35,11 @@ public interface EntrypointContainer {
* Returns the mod that provided this entrypoint.
*/
ModContainer getProvider();
+
+ /**
+ * Returns a string representation of the entrypoint's definition.
+ */
+ default String getDefinition() {
+ return "";
+ }
}
diff --git a/src/main/java/org/quiltmc/loader/impl/QuiltLoaderImpl.java b/src/main/java/org/quiltmc/loader/impl/QuiltLoaderImpl.java
index 0dd71764e..ca83ca2aa 100644
--- a/src/main/java/org/quiltmc/loader/impl/QuiltLoaderImpl.java
+++ b/src/main/java/org/quiltmc/loader/impl/QuiltLoaderImpl.java
@@ -131,7 +131,7 @@ public final class QuiltLoaderImpl {
public static final int ASM_VERSION = Opcodes.ASM9;
- public static final String VERSION = "0.26.4-beta.1";
+ public static final String VERSION = "0.26.4";
public static final String MOD_ID = "quilt_loader";
public static final String DEFAULT_MODS_DIR = "mods";
public static final String DEFAULT_CACHE_DIR = ".cache";
diff --git a/src/main/java/org/quiltmc/loader/impl/entrypoint/EntrypointStorage.java b/src/main/java/org/quiltmc/loader/impl/entrypoint/EntrypointStorage.java
index a068867f1..a298c53ef 100644
--- a/src/main/java/org/quiltmc/loader/impl/entrypoint/EntrypointStorage.java
+++ b/src/main/java/org/quiltmc/loader/impl/entrypoint/EntrypointStorage.java
@@ -39,6 +39,8 @@ interface Entry {
boolean isOptional();
ModContainerExt getModContainer();
+
+ String getDefinition();
}
@SuppressWarnings("deprecation")
@@ -87,6 +89,11 @@ public boolean isOptional() {
public ModContainerExt getModContainer() {
return mod;
}
+
+ @Override
+ public String getDefinition() {
+ return value;
+ }
}
private static final class NewEntry implements Entry {
@@ -131,6 +138,11 @@ public boolean isOptional() {
public ModContainerExt getModContainer() {
return mod;
}
+
+ @Override
+ public String getDefinition() {
+ return value;
+ }
}
private final Map> entryMap = new HashMap<>();
diff --git a/src/main/java/org/quiltmc/loader/impl/entrypoint/EntrypointUtils.java b/src/main/java/org/quiltmc/loader/impl/entrypoint/EntrypointUtils.java
index 882bd594c..7bfd9d7a9 100644
--- a/src/main/java/org/quiltmc/loader/impl/entrypoint/EntrypointUtils.java
+++ b/src/main/java/org/quiltmc/loader/impl/entrypoint/EntrypointUtils.java
@@ -63,8 +63,8 @@ private static void invoke0(String name, Class type, Consumer new RuntimeException(String.format("Could not execute entrypoint stage '%s' due to errors, provided by '%s'!",
- name, container.getProvider().metadata().id()),
+ exc -> new RuntimeException(String.format("Could not execute entrypoint stage '%s' due to errors, provided by '%s' at '%s'!",
+ name, container.getProvider().metadata().id(), container.getDefinition()),
exc));
}
}
diff --git a/src/main/java/org/quiltmc/loader/impl/launch/common/QuiltMixinBootstrap.java b/src/main/java/org/quiltmc/loader/impl/launch/common/QuiltMixinBootstrap.java
index f46e88047..e5352a99f 100644
--- a/src/main/java/org/quiltmc/loader/impl/launch/common/QuiltMixinBootstrap.java
+++ b/src/main/java/org/quiltmc/loader/impl/launch/common/QuiltMixinBootstrap.java
@@ -147,7 +147,7 @@ public static final class MixinConfigDecorator {
// maximum loader version and bundled fabric mixin version, DESCENDING ORDER, LATEST FIRST
// loader versions with new mixin versions need to be added here
- // addVersion("0.13", FabricUtil.COMPATIBILITY_0_11_0); // example for next entry (latest first!)
+ addVersion("0.16.0", FabricUtil.COMPATIBILITY_0_14_0);
addVersion("0.12.0-", FabricUtil.COMPATIBILITY_0_10_0);
}
@@ -173,9 +173,11 @@ public static int getMixinCompat(boolean isFabric, ModMetadata metadata) {
List reqIntervals = Collections.singletonList(VersionInterval.INFINITE);
if (!isFabric) {
- // quilt or builtin mod, we can assume it uses latest compat
- Log.debug(LogCategory.MIXIN, "Assuming Quilt mod %s uses latest mixin compatibility", metadata.id());
- return FabricUtil.COMPATIBILITY_LATEST;
+ // quilt or builtin mod, we can assume it uses latest (0.10.0 at the time) compat
+ // Except since , we can't assume that anymore!
+ // TODO - Handle Quilt mods like Fabric mods but with our own version ranges
+ Log.debug(LogCategory.MIXIN, "Assuming Quilt mod %s uses 0.10.0 mixin compatibility", metadata.id());
+ return FabricUtil.COMPATIBILITY_0_10_0;
}
FabricLoaderModMetadata fabricMeta = ((InternalModMetadata) metadata).asFabricModMetadata();
@@ -202,11 +204,10 @@ public static int getMixinCompat(boolean isFabric, ModMetadata metadata) {
if (minLoaderVersion.compareTo(version.loaderVersion) >= 0) { // lower bound is >= current version
Log.debug(LogCategory.MIXIN, "Mod %s requires loader version %s, using mixin compatibility %s", metadata.id(), minLoaderVersion, version.mixinVersion);
return version.mixinVersion;
- } else {
- Log.debug(LogCategory.MIXIN, "Mod %s requires loader version %s, using 0.9.2 mixin compatability", metadata.id(), minLoaderVersion);
- return FabricUtil.COMPATIBILITY_0_9_2;
}
}
+ Log.debug(LogCategory.MIXIN, "Mod %s requires loader version %s, using 0.9.2 mixin compatability", metadata.id(), minLoaderVersion);
+ return FabricUtil.COMPATIBILITY_0_9_2;
}
// Mod doesn't declare a dependency on a loader version; use oldest mixin compat version
diff --git a/src/main/java/org/quiltmc/loader/impl/launch/knot/MixinContainerHandleMod.java b/src/main/java/org/quiltmc/loader/impl/launch/knot/MixinContainerHandleMod.java
deleted file mode 100644
index 99ad0d18a..000000000
--- a/src/main/java/org/quiltmc/loader/impl/launch/knot/MixinContainerHandleMod.java
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * Copyright 2016 FabricMC
- * Copyright 2022-2023 QuiltMC
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.quiltmc.loader.impl.launch.knot;
-
-import java.util.Collection;
-import java.util.Collections;
-
-import org.quiltmc.loader.impl.util.QuiltLoaderInternal;
-import org.quiltmc.loader.impl.util.QuiltLoaderInternalType;
-import org.spongepowered.asm.launch.platform.container.IContainerHandle;
-
-@QuiltLoaderInternal(QuiltLoaderInternalType.LEGACY_EXPOSED)
-public class MixinContainerHandleMod implements IContainerHandle {
- @Override
- public String getAttribute(String name) {
- return null;
- }
-
- @Override
- public Collection getNestedContainers() {
- return Collections.emptyList();
- }
-}
diff --git a/src/main/java/org/quiltmc/loader/impl/launch/knot/MixinServiceKnot.java b/src/main/java/org/quiltmc/loader/impl/launch/knot/MixinServiceKnot.java
index 88cea02e1..e92cd42f4 100644
--- a/src/main/java/org/quiltmc/loader/impl/launch/knot/MixinServiceKnot.java
+++ b/src/main/java/org/quiltmc/loader/impl/launch/knot/MixinServiceKnot.java
@@ -85,9 +85,14 @@ public ClassNode getClassNode(String name) throws ClassNotFoundException, IOExce
@Override
public ClassNode getClassNode(String name, boolean runTransformers) throws ClassNotFoundException, IOException {
+ return getClassNode(name, runTransformers, 0);
+ }
+
+ @Override
+ public ClassNode getClassNode(String name, boolean runTransformers, int readerFlags) throws ClassNotFoundException, IOException {
ClassReader reader = new ClassReader(getClassBytes(name, runTransformers));
ClassNode node = new ClassNode();
- reader.accept(node, 0);
+ reader.accept(node, readerFlags);
return node;
}
diff --git a/src/main/java/org/quiltmc/loader/impl/plugin/QuiltPluginClassLoader.java b/src/main/java/org/quiltmc/loader/impl/plugin/QuiltPluginClassLoader.java
index 3586e9dbe..f2133fea2 100644
--- a/src/main/java/org/quiltmc/loader/impl/plugin/QuiltPluginClassLoader.java
+++ b/src/main/java/org/quiltmc/loader/impl/plugin/QuiltPluginClassLoader.java
@@ -48,7 +48,11 @@ public QuiltPluginClassLoader(QuiltPluginContextImpl context, ClassLoader parent
@Override
protected Class> loadClass(String name, boolean resolve) throws ClassNotFoundException {
- Class> c = loadClassInner(name);
+ Class> c = findLoadedClass(name);
+ if (c != null) {
+ return c;
+ }
+ c = loadClassInner(name);
if (c == null) {
return super.loadClass(name, resolve);
}
diff --git a/src/main/java/org/quiltmc/loader/impl/plugin/QuiltPluginManagerImpl.java b/src/main/java/org/quiltmc/loader/impl/plugin/QuiltPluginManagerImpl.java
index 512c940ae..f7845a9ad 100644
--- a/src/main/java/org/quiltmc/loader/impl/plugin/QuiltPluginManagerImpl.java
+++ b/src/main/java/org/quiltmc/loader/impl/plugin/QuiltPluginManagerImpl.java
@@ -1590,24 +1590,37 @@ ModSolveResultImpl getPartialSolution() throws ModSolvingError, TimeoutException
Map, LoadOptionResult>> extraResults;
final Map, Map