Skip to content

Commit 0faedcb

Browse files
committed
mixin: Add support for MixinBooter
This commit adds stubs and custom functionality as required by MixinBooter to not crash when booting. Mods which rely on other features only available in MixinBooter's Mixin fork or which rely on the Mixin version shipped with MixinBooter, may of course still not function properly. Although we are not currently aware of any such mod.
1 parent 88a7b3e commit 0faedcb

File tree

9 files changed

+154
-0
lines changed

9 files changed

+154
-0
lines changed
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
package gg.essential.mixincompat.cleanroom;
2+
3+
import gg.essential.CompatMixin;
4+
import org.spongepowered.asm.mixin.transformer.ClassInfo;
5+
6+
@CompatMixin(ClassInfo.class)
7+
public class ClassInfoCompat {
8+
// Method added in Cleanroom's Mixin fork, and MixinBooter calls it
9+
// https://github.com/CleanroomMC/MixinBooter/blob/05fc6c7b4b36a714c90eb4cc2f2364c681da0bc8/src/main/java/zone/rong/mixinbooter/fix/MixinFixer.java#L35
10+
// https://github.com/CleanroomMC/MixinBooter-UniMix/blob/9d4b487ed32501137645cdf0da484b076f0bfaf4/src/main/java/org/spongepowered/asm/mixin/transformer/ClassInfo.java#L2239
11+
public static void registerCallback(Callback callback) {
12+
// It seems like MixinBooter uses these callbacks to replace init-phase mixins targeting Forge's Loader to
13+
// make it possible to target ordinary mod classes via mixins.
14+
// Given we already add back in the methods which those old mixins call, it should be fine for us to just
15+
// allow them to apply as they also would without MixinBooter, and it should just work.
16+
// This method can therefore just do nothing.
17+
}
18+
19+
@CompatMixin(target = "org.spongepowered.asm.mixin.transformer.ClassInfo$Callback", createTarget = true)
20+
public interface Callback {
21+
void onInit(ClassInfo classInfo);
22+
}
23+
}
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
package gg.essential.mixincompat.cleanroom;
2+
3+
import gg.essential.CompatMixin;
4+
import org.spongepowered.asm.launch.GlobalProperties;
5+
6+
@CompatMixin(GlobalProperties.Keys.class)
7+
public class GlobalPropertiesKeysCompat {
8+
// Required for MixinBooter to not crash on boot
9+
// https://github.com/CleanroomMC/MixinBooter/blob/05fc6c7b4b36a714c90eb4cc2f2364c681da0bc8/src/main/java/zone/rong/mixinbooter/MixinBooterPlugin.java#L87
10+
// https://github.com/CleanroomMC/MixinBooter/blob/05fc6c7b4b36a714c90eb4cc2f2364c681da0bc8/src/main/java/zone/rong/mixinbooter/MixinBooterPlugin.java#L198
11+
// https://github.com/CleanroomMC/MixinBooter-UniMix/blob/9d4b487ed32501137645cdf0da484b076f0bfaf4/src/main/java/org/spongepowered/asm/launch/GlobalProperties.java#L55
12+
public static final GlobalProperties.Keys CLEANROOM_DISABLE_MIXIN_CONFIGS = GlobalProperties.Keys.of("mixin.cleanroom.disablemixinconfigs");
13+
}
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
package gg.essential.mixincompat.cleanroom;
2+
3+
import gg.essential.CompatMixin;
4+
import org.spongepowered.asm.mixin.extensibility.IMixinConfig;
5+
import org.spongepowered.asm.service.IMixinService;
6+
7+
import java.util.List;
8+
9+
// Interface added in Cleanroom's Mixin fork to expose certain internals
10+
// https://github.com/CleanroomMC/MixinBooter-UniMix/blob/9d4b487ed32501137645cdf0da484b076f0bfaf4/src/main/java/org/spongepowered/asm/mixin/extensibility/IMixinProcessor.java
11+
@CompatMixin(target = "org.spongepowered.asm.mixin.extensibility.IMixinProcessor", createTarget = true)
12+
public interface IMixinProcessor {
13+
IMixinService getMixinService();
14+
List<IMixinConfig> getMixinConfigs();
15+
List<IMixinConfig> getPendingMixinConfigs();
16+
}
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
package gg.essential.mixincompat.cleanroom;
2+
3+
import gg.essential.CompatMixin;
4+
import org.spongepowered.asm.mixin.transformer.IMixinTransformer;
5+
6+
@CompatMixin(IMixinTransformer.class)
7+
public interface IMixinTransformerCompat {
8+
// Method which exists in Cleanroom's Mixin fork, and MixinBooter crashes if it's missing
9+
// https://github.com/CleanroomMC/MixinBooter/blob/05fc6c7b4b36a714c90eb4cc2f2364c681da0bc8/src/main/java/zone/rong/mixinbooter/mixin/LoadControllerMixin.java#L115
10+
default IMixinProcessor getProcessor() { throw new UnsupportedOperationException(); }
11+
}
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
package gg.essential.mixincompat.cleanroom;
2+
3+
import gg.essential.CompatMixin;
4+
import gg.essential.CompatShadow;
5+
import org.spongepowered.asm.launch.GlobalProperties;
6+
import org.spongepowered.asm.mixin.MixinEnvironment;
7+
import org.spongepowered.asm.mixin.transformer.Config;
8+
9+
import java.util.Collections;
10+
import java.util.Set;
11+
12+
@CompatMixin(target = "org.spongepowered.asm.mixin.transformer.MixinConfig")
13+
public class MixinConfigCompat {
14+
// See GlobalPropertiesKeysCompat
15+
// https://github.com/CleanroomMC/MixinBooter-UniMix/blob/9d4b487ed32501137645cdf0da484b076f0bfaf4/src/main/java/org/spongepowered/asm/mixin/transformer/MixinConfig.java#L1400
16+
static Config create(String configFile, MixinEnvironment outer) {
17+
Set<String> disabledMixinConfigs = GlobalProperties.get(GlobalPropertiesKeysCompat.CLEANROOM_DISABLE_MIXIN_CONFIGS, Collections.emptySet());
18+
if (disabledMixinConfigs.contains(configFile)) {
19+
return null;
20+
}
21+
return create$original(configFile, outer);
22+
}
23+
24+
@CompatShadow(original = "create")
25+
static Config create$original(String configFile, MixinEnvironment outer) { throw new LinkageError(); }
26+
}
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
package gg.essential.mixincompat.cleanroom;
2+
3+
import gg.essential.CompatMixin;
4+
import gg.essential.CompatShadow;
5+
import org.spongepowered.asm.mixin.extensibility.IMixinConfig;
6+
import org.spongepowered.asm.service.IMixinService;
7+
8+
import java.util.Collections;
9+
import java.util.List;
10+
11+
@CompatMixin(target = "org.spongepowered.asm.mixin.transformer.MixinProcessor")
12+
public class MixinProcessorCompat implements IMixinProcessor {
13+
@CompatShadow
14+
private IMixinService service;
15+
@CompatShadow
16+
private List<IMixinConfig> configs;
17+
@CompatShadow
18+
private List<IMixinConfig> pendingConfigs;
19+
20+
// See IMixinTransformerCompat
21+
@Override public IMixinService getMixinService() { return service; }
22+
@Override public List<IMixinConfig> getMixinConfigs() { return Collections.unmodifiableList(configs); }
23+
@Override public List<IMixinConfig> getPendingMixinConfigs() { return Collections.unmodifiableList(pendingConfigs); }
24+
}
Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
package gg.essential.mixincompat.cleanroom;
2+
3+
import gg.essential.CompatMixin;
4+
import gg.essential.CompatShadow;
5+
6+
@CompatMixin(target = "org.spongepowered.asm.mixin.transformer.MixinTransformer")
7+
public class MixinTransformerCompat {
8+
@CompatShadow
9+
private MixinProcessorCompat processor;
10+
11+
// Overrides the interface method added in IMixinTransformerCompat
12+
public IMixinProcessor getProcessor() {
13+
return processor;
14+
}
15+
}
Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
package gg.essential.mixincompat.cleanroom;
2+
3+
import gg.essential.CompatAccessTransformer;
4+
import gg.essential.CompatMixin;
5+
import gg.essential.CompatShadow;
6+
import gg.essential.mixincompat.MixinTransformerCompat;
7+
import org.objectweb.asm.Opcodes;
8+
import org.spongepowered.asm.mixin.transformer.Proxy;
9+
10+
@CompatMixin(Proxy.class)
11+
public class ProxyCompat {
12+
// This field is public in Cleanroom's Mixin fork, and MixinBooter accesses it as such
13+
// https://github.com/CleanroomMC/MixinBooter/blob/05fc6c7b4b36a714c90eb4cc2f2364c681da0bc8/src/main/java/zone/rong/mixinbooter/mixin/LoadControllerMixin.java#L115
14+
@CompatShadow
15+
@CompatAccessTransformer(add = Opcodes.ACC_PUBLIC, remove = Opcodes.ACC_PRIVATE)
16+
private static MixinTransformerCompat transformer;
17+
}
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
/**
2+
* This package contains patches to make Cleanroom's MixinBooter (which relies Cleanroom's Mixin fork) not crash
3+
* (whether it is fully functional is a different question; it at least appears to be mostly functional)
4+
* when its custom Mixin fork is replaced by our patched Mixin.
5+
*
6+
* @link https://github.com/CleanroomMC/MixinBooter/tree/05fc6c7b4b36a714c90eb4cc2f2364c681da0bc8/
7+
* @link https://github.com/CleanroomMC/MixinBooter-UniMix/tree/9d4b487ed32501137645cdf0da484b076f0bfaf4/
8+
*/
9+
package gg.essential.mixincompat.cleanroom;

0 commit comments

Comments
 (0)