diff options
| author | shedaniel <daniel@shedaniel.me> | 2022-09-12 23:05:35 +0800 |
|---|---|---|
| committer | shedaniel <daniel@shedaniel.me> | 2022-09-12 23:05:35 +0800 |
| commit | d938b32705594c995ad9f82b0f0b64897b6c423f (patch) | |
| tree | e2cd09be1630093d69d6ce7d1942d861efa848f9 | |
| parent | 47896cdd0e1d440ca85aef3cc8f24b229a18c949 (diff) | |
| download | RoughlyEnoughItems-feature/obfuscate.tar.gz RoughlyEnoughItems-feature/obfuscate.tar.bz2 RoughlyEnoughItems-feature/obfuscate.zip | |
Obfuscate REI Internalsfeature/obfuscate
16 files changed, 231 insertions, 33 deletions
diff --git a/api/src/main/java/me/shedaniel/rei/impl/ClientInternals.java b/api/src/main/java/me/shedaniel/rei/impl/ClientInternals.java index 36456399b..0d0fd45f4 100644 --- a/api/src/main/java/me/shedaniel/rei/impl/ClientInternals.java +++ b/api/src/main/java/me/shedaniel/rei/impl/ClientInternals.java @@ -53,6 +53,7 @@ import org.jetbrains.annotations.ApiStatus; import org.jetbrains.annotations.Nullable; import java.lang.reflect.Field; +import java.lang.reflect.ParameterizedType; import java.util.Collection; import java.util.List; import java.util.function.BiConsumer; @@ -84,7 +85,18 @@ public final class ClientInternals { @ApiStatus.Internal public static <T> void attachInstance(T instance, Class<T> clazz) { - attachInstanceSupplier(instance, clazz.getSimpleName()); + try { + for (Field field : ClientInternals.class.getDeclaredFields()) { + if (field.getGenericType() instanceof ParameterizedType && ((ParameterizedType) field.getGenericType()).getActualTypeArguments()[0] == clazz) { + field.setAccessible(true); + field.set(null, (Supplier<T>) () -> instance); + return; + } + } + throw new RuntimeException("Failed to attach " + instance + " with field type: " + clazz); + } catch (IllegalAccessException e) { + throw new RuntimeException(e); + } } @ApiStatus.Internal diff --git a/api/src/main/java/me/shedaniel/rei/impl/Internals.java b/api/src/main/java/me/shedaniel/rei/impl/Internals.java index 1e64c2c57..c191a5b31 100644 --- a/api/src/main/java/me/shedaniel/rei/impl/Internals.java +++ b/api/src/main/java/me/shedaniel/rei/impl/Internals.java @@ -41,6 +41,7 @@ import net.minecraft.util.Unit; import org.jetbrains.annotations.ApiStatus; import java.lang.reflect.Field; +import java.lang.reflect.ParameterizedType; import java.util.function.Function; import java.util.function.Supplier; @@ -62,7 +63,18 @@ public final class Internals { @ApiStatus.Internal public static <T> void attachInstance(T instance, Class<T> clazz) { - attachInstanceSupplier(instance, clazz.getSimpleName()); + try { + for (Field field : Internals.class.getDeclaredFields()) { + if (field.getGenericType() instanceof ParameterizedType && ((ParameterizedType) field.getGenericType()).getActualTypeArguments()[0] == clazz) { + field.setAccessible(true); + field.set(null, (Supplier<T>) () -> instance); + return; + } + } + throw new RuntimeException("Failed to attach " + instance + " with field type: " + clazz); + } catch (IllegalAccessException e) { + throw new RuntimeException(e); + } } @ApiStatus.Internal diff --git a/build.gradle b/build.gradle index 3fefac531..433f1f4db 100755 --- a/build.gradle +++ b/build.gradle @@ -1,3 +1,17 @@ +//file:noinspection UnnecessaryQualifiedReference +buildscript { + repositories { + maven { url "https://maven.architectury.dev/" } + mavenCentral() + mavenLocal() + } + + dependencies { + classpath "com.guardsquare:proguard-gradle:7.2.1" + classpath "dev.architectury:architectury-transformer:5.2.9999" + } +} + plugins { id("architectury-plugin") version("3.4-SNAPSHOT") id("dev.architectury.loom") version("0.12.0-SNAPSHOT") apply false @@ -158,3 +172,146 @@ task releaseOnCf { dependsOn project("fabric").tasks.getByName("publishUnified") } } + +def randomString(len) { + def AB = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz" + def rnd = new java.security.SecureRandom() + return (0..len).toList().collect { AB.charAt(rnd.nextInt(AB.length())) }.join("") +} + +rootProject.file(".gradle/proguard-dictionary.txt").delete() +rootProject.file(".gradle/proguard-dictionary.txt").write((0..1000).toList().collect { randomString(10) }.join("\n")) + +["fabric", "forge"].each { loader -> + project(":$loader") { + afterEvaluate { + def proguardJarOut = file(tasks.getByName("shadowJar").archiveFile.get().getAsFile().absolutePath.replace(".jar", "-min.jar")) + + task proguardJar(type: proguard.gradle.ProGuardTask, dependsOn: ["shadowJar"]) { + doFirst { + if (proguardJarOut.exists()) { + proguardJarOut.delete() + } + } + + verbose() + injars tasks.getByName("shadowJar").archiveFile.get().getAsFile() + outjars proguardJarOut + libraryjars files(configurations.compileClasspath) + libraryjars "${System.getProperty('java.home')}/jmods/java.base.jmod", jarfilter: '!**.jar', filter: '!module-info.class' + dontshrink() + keep "class me.shedaniel.rei.api.** { *; }" + keep "class me.shedaniel.rei.plugin.** { *; }" + keepclassmembers "class * { void onInitialize(); void onInitializeClient(); }" + keepclassmembers "class * { @net.minecraft.obfuscate.DontObfuscate <fields>; @net.minecraft.obfuscate.DontObfuscate <methods>; }" + keepclassmembers "class me.shedaniel.rei.impl.*Internals { <fields>; }" + keepclassmembers "class me.shedaniel.rei.impl.client.config.ConfigObjectImpl* { <fields>; }" + dontwarn "me.shedaniel.rei.impl.init.RoughlyEnoughItemsInitializer" + dontwarn "me.shedaniel.rei.plugin.client.DefaultClientPlugin" + obfuscationdictionary rootProject.file(".gradle/proguard-dictionary.txt") + classobfuscationdictionary rootProject.file(".gradle/proguard-dictionary.txt") + repackageclasses "me.shedaniel.rei.impl.${randomString(10)}" + keep "class me.shedaniel.rei.mixin.$loader.** { *; }" + keepattributes "Signature,SourceFile,LineNumberTable,Exceptions,InnerClasses,*Annotation*" + printmapping file(".gradle/proguard-mapping.txt") + optimizationpasses 5 + optimizations "**" + allowaccessmodification() + + doLast { + try (def access = dev.architectury.transformer.input.OpenedFileAccess.ofJar(proguardJarOut.toPath())) { + dev.architectury.transformer.Transform.runTransformers( + new dev.architectury.transformer.transformers.base.edit.SimpleTransformerContext(args -> { throw new IllegalStateException(); }, + true, false, true), + dev.architectury.transformer.transformers.ClasspathProvider.of(files(configurations.compileClasspath).collect { it.toPath() }), + proguardJarOut.name, + access, transformers(loader)) + } + } + } + + tasks.prepareRemapJar { + inputFile.set proguardJarOut + dependsOn proguardJar + } + + tasks.remapJar { + input.set proguardJarOut + dependsOn proguardJar + } + } + } +} + +def transformers(loader) { + def map = new HashMap<String, String>(); + file(".gradle/proguard-mapping.txt").eachLine { + if (!it.startsWith(" ")) { + map[it.split(" -> ")[0]] = it.split(" -> ")[1].split(":")[0] + } + } + return [new dev.architectury.transformer.transformers.base.ClassEditTransformer() { + @Override + dev.architectury.transformer.shadowed.impl.org.objectweb.asm.tree.ClassNode doEdit(String name, dev.architectury.transformer.shadowed.impl.org.objectweb.asm.tree.ClassNode node) { + if (dev.architectury.transformer.Transform.trimSlashes(name).startsWith("me/shedaniel/rei/impl")) { + if (node.invisibleAnnotations == null || !node.invisibleAnnotations.any { it.desc == "Lorg/jetbrains/annotations/ApiStatus\$Internal;" }) { + if (node.invisibleAnnotations == null) node.invisibleAnnotations = new ArrayList<>() + node.invisibleAnnotations.add(new dev.architectury.transformer.shadowed.impl.org.objectweb.asm.tree.AnnotationNode("Lorg/jetbrains/annotations/ApiStatus\$Internal;")) + } + } + + node.methods.forEach { method -> + method.instructions.forEach { insn -> + if (insn.opcode == dev.architectury.transformer.shadowed.impl.org.objectweb.asm.Opcodes.LDC + && insn instanceof dev.architectury.transformer.shadowed.impl.org.objectweb.asm.tree.LdcInsnNode + && insn.cst instanceof String) { + if (insn.cst.contains("%s")) { + def replaced = insn.cst.replace("%s", loader) + + if (map.containsKey(replaced)) { + insn.cst = map[replaced] + } + } else { + insn.cst = map.getOrDefault(insn.cst, insn.cst) + } + } + } + } + + return node + } + }, new dev.architectury.transformer.transformers.base.AssetEditTransformer() { + @Override + void doEdit(dev.architectury.transformer.transformers.base.edit.TransformerContext context, dev.architectury.transformer.input.FileAccess output) throws Exception { + def renames = [] + output.handle((java.util.function.Consumer<String>) { String name -> + def trimmed = dev.architectury.transformer.Transform.trimSlashes(name) + if (trimmed.startsWith("META-INF/services/")) { + output.modifyFile(trimmed) { bytes -> + new String(bytes).split("\n").collect { map[it] ?: it }.join("\n").bytes + } + + def remapped = map[trimmed.substring("META-INF/services/".length())] + if (remapped != null) { + renames << [trimmed, "META-INF/services/$remapped"] + } + } + }) + renames.each { + output.addFile(it[1], output.getFile(it[0])) + output.deleteFile(it[0]) + } + + output.modifyFile("fabric.mod.json") { bytes -> + new String(bytes).split("\n").collect { + map.forEach { k, v -> + it = it.replace("\"$k\"", "\"$v\"") + it = it.replace("\"$k::onInitialize\"", "\"$v::onInitialize\"") + it = it.replace("\"$k::onInitializeClient\"", "\"$v::onInitializeClient\"") + } + it + }.join("\n").bytes + } + } + }] +} diff --git a/default-plugin/src/main/java/me/shedaniel/rei/plugin/client/favorites/CommandSender.java b/default-plugin/src/main/java/me/shedaniel/rei/plugin/client/favorites/CommandSender.java index e0ae0ba1e..5d33a4ec3 100644 --- a/default-plugin/src/main/java/me/shedaniel/rei/plugin/client/favorites/CommandSender.java +++ b/default-plugin/src/main/java/me/shedaniel/rei/plugin/client/favorites/CommandSender.java @@ -30,7 +30,8 @@ import java.lang.reflect.InvocationTargetException; class CommandSender { static void sendCommand(String command) { try { - Class.forName("me.shedaniel.rei.impl.client.%s.CommandSenderImpl".formatted(Platform.isForge() ? "forge" : "fabric")) + String s = "me.shedaniel.rei.impl.client.%s.CommandSenderImpl"; + Class.forName(s.contains("%s") ? s.formatted(Platform.isForge() ? "forge" : "fabric") : s) .getDeclaredMethod("sendCommand", String.class).invoke(null, command); } catch (IllegalAccessException | ClassNotFoundException | NoSuchMethodException | InvocationTargetException e) { throw new RuntimeException(e); diff --git a/default-plugin/src/main/java/me/shedaniel/rei/plugin/common/displays/crafting/DefaultCraftingDisplay.java b/default-plugin/src/main/java/me/shedaniel/rei/plugin/common/displays/crafting/DefaultCraftingDisplay.java index 84f4b50e1..8e897ef48 100644 --- a/default-plugin/src/main/java/me/shedaniel/rei/plugin/common/displays/crafting/DefaultCraftingDisplay.java +++ b/default-plugin/src/main/java/me/shedaniel/rei/plugin/common/displays/crafting/DefaultCraftingDisplay.java @@ -68,7 +68,8 @@ public abstract class DefaultCraftingDisplay<C extends Recipe<?>> extends BasicD static { try { - Class.forName("me.shedaniel.rei.plugin.common.displays.crafting.%s.DefaultCraftingDisplayImpl".formatted(Platform.isForge() ? "forge" : "fabric")) + String s = "me.shedaniel.rei.plugin.common.displays.crafting.%s.DefaultCraftingDisplayImpl"; + Class.forName(s.contains("%s") ? s.formatted(Platform.isForge() ? "forge" : "fabric") : s) .getDeclaredMethod("registerPlatformSizeProvider") .invoke(null); } catch (IllegalAccessException | ClassNotFoundException | NoSuchMethodException | InvocationTargetException e) { diff --git a/fabric/src/main/java/me/shedaniel/rei/impl/client/fabric/CommandSenderImpl.java b/fabric/src/main/java/me/shedaniel/rei/impl/client/fabric/CommandSenderImpl.java index 84212209e..007b20ca2 100644 --- a/fabric/src/main/java/me/shedaniel/rei/impl/client/fabric/CommandSenderImpl.java +++ b/fabric/src/main/java/me/shedaniel/rei/impl/client/fabric/CommandSenderImpl.java @@ -27,12 +27,14 @@ import dev.architectury.platform.Platform; import net.fabricmc.loader.api.FabricLoader; import net.minecraft.client.Minecraft; import net.minecraft.client.player.LocalPlayer; +import net.minecraft.obfuscate.DontObfuscate; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; -public class CommandSenderImpl { - public static void sendCommand(String command) { +public interface CommandSenderImpl { + @DontObfuscate + static void sendCommand(String command) { LocalPlayer player = Minecraft.getInstance().player; if (player == null) return; String methodName = "method_44099"; diff --git a/fabric/src/main/java/me/shedaniel/rei/impl/client/gui/credits/fabric/CreditsScreenImpl.java b/fabric/src/main/java/me/shedaniel/rei/impl/client/gui/credits/fabric/CreditsScreenImpl.java index f148272e0..9fba04492 100644 --- a/fabric/src/main/java/me/shedaniel/rei/impl/client/gui/credits/fabric/CreditsScreenImpl.java +++ b/fabric/src/main/java/me/shedaniel/rei/impl/client/gui/credits/fabric/CreditsScreenImpl.java @@ -27,14 +27,16 @@ import com.google.common.collect.Lists; import me.shedaniel.rei.impl.client.gui.credits.CreditsScreen; import net.fabricmc.loader.api.FabricLoader; import net.fabricmc.loader.api.metadata.CustomValue; +import net.minecraft.obfuscate.DontObfuscate; import net.minecraft.util.Tuple; import java.util.Comparator; import java.util.List; import java.util.stream.Collectors; -public class CreditsScreenImpl { - public static void fillTranslators(Exception[] exception, List<Tuple<String, List<CreditsScreen.TranslatorEntry>>> translators) { +public interface CreditsScreenImpl { + @DontObfuscate + static void fillTranslators(Exception[] exception, List<Tuple<String, List<CreditsScreen.TranslatorEntry>>> translators) { FabricLoader.getInstance().getModContainer("roughlyenoughitems").ifPresent(rei -> { try { if (rei.getMetadata().containsCustomValue("rei:translators")) { diff --git a/fabric/src/main/java/me/shedaniel/rei/plugin/common/displays/crafting/fabric/DefaultCraftingDisplayImpl.java b/fabric/src/main/java/me/shedaniel/rei/plugin/common/displays/crafting/fabric/DefaultCraftingDisplayImpl.java index 60dff699b..b76866195 100644 --- a/fabric/src/main/java/me/shedaniel/rei/plugin/common/displays/crafting/fabric/DefaultCraftingDisplayImpl.java +++ b/fabric/src/main/java/me/shedaniel/rei/plugin/common/displays/crafting/fabric/DefaultCraftingDisplayImpl.java @@ -23,7 +23,10 @@ package me.shedaniel.rei.plugin.common.displays.crafting.fabric; -public class DefaultCraftingDisplayImpl { - public static void registerPlatformSizeProvider() { +import net.minecraft.obfuscate.DontObfuscate; + +public interface DefaultCraftingDisplayImpl { + @DontObfuscate + static void registerPlatformSizeProvider() { } } diff --git a/forge/build.gradle b/forge/build.gradle index 37cf85e1f..b62ac7829 100644 --- a/forge/build.gradle +++ b/forge/build.gradle @@ -56,13 +56,6 @@ loom { } forge { - localMods { - jeiInternalsWorkaround { - add(project(":jei-compatibility-layer").sourceSets.main) - add(project(":jei-internals-workaround").sourceSets.main) - } - } - mixinConfig "rei.mixins.json" } } @@ -74,8 +67,6 @@ dependencies { modApi("me.shedaniel.cloth:cloth-config-forge:${cloth_config_version}") modApi("dev.architectury:architectury-forge:${architectury_version}") - runtimeClasspath(project(path: ":jei-internals-workaround", configuration: "namedElements")) { transitive false } - depProjects.forEach { common(project(path: it, configuration: "namedElements")) { transitive false } shadowCommon(project(path: it, configuration: "transformProductionForge")) { transitive false } diff --git a/forge/src/main/java/me/shedaniel/rei/impl/client/forge/CommandSenderImpl.java b/forge/src/main/java/me/shedaniel/rei/impl/client/forge/CommandSenderImpl.java index 83253fc9c..44b7586fc 100644 --- a/forge/src/main/java/me/shedaniel/rei/impl/client/forge/CommandSenderImpl.java +++ b/forge/src/main/java/me/shedaniel/rei/impl/client/forge/CommandSenderImpl.java @@ -25,13 +25,15 @@ package me.shedaniel.rei.impl.client.forge; import net.minecraft.client.Minecraft; import net.minecraft.client.player.LocalPlayer; +import net.minecraft.obfuscate.DontObfuscate; import net.minecraftforge.fml.util.ObfuscationReflectionHelper; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; -public class CommandSenderImpl { - public static void sendCommand(String command) { +public interface CommandSenderImpl { + @DontObfuscate + static void sendCommand(String command) { LocalPlayer player = Minecraft.getInstance().player; if (player == null) return; Method method = null; diff --git a/forge/src/main/java/me/shedaniel/rei/impl/client/gui/credits/forge/CreditsScreenImpl.java b/forge/src/main/java/me/shedaniel/rei/impl/client/gui/credits/forge/CreditsScreenImpl.java index ef53fe3b1..9265b21fa 100644 --- a/forge/src/main/java/me/shedaniel/rei/impl/client/gui/credits/forge/CreditsScreenImpl.java +++ b/forge/src/main/java/me/shedaniel/rei/impl/client/gui/credits/forge/CreditsScreenImpl.java @@ -24,11 +24,13 @@ package me.shedaniel.rei.impl.client.gui.credits.forge; import me.shedaniel.rei.impl.client.gui.credits.CreditsScreen; +import net.minecraft.obfuscate.DontObfuscate; import net.minecraft.util.Tuple; import java.util.List; -public class CreditsScreenImpl { - public static void fillTranslators(Exception[] exception, List<Tuple<String, List<CreditsScreen.TranslatorEntry>>> translators) { +public interface CreditsScreenImpl { + @DontObfuscate + static void fillTranslators(Exception[] exception, List<Tuple<String, List<CreditsScreen.TranslatorEntry>>> translators) { } } diff --git a/forge/src/main/java/me/shedaniel/rei/plugin/common/displays/crafting/forge/DefaultCraftingDisplayImpl.java b/forge/src/main/java/me/shedaniel/rei/plugin/common/displays/crafting/forge/DefaultCraftingDisplayImpl.java index 9f5faa713..d3d18639a 100644 --- a/forge/src/main/java/me/shedaniel/rei/plugin/common/displays/crafting/forge/DefaultCraftingDisplayImpl.java +++ b/forge/src/main/java/me/shedaniel/rei/plugin/common/displays/crafting/forge/DefaultCraftingDisplayImpl.java @@ -25,10 +25,12 @@ package me.shedaniel.rei.plugin.common.displays.crafting.forge; import me.shedaniel.rei.plugin.common.displays.crafting.CraftingRecipeSizeProvider; import me.shedaniel.rei.plugin.common.displays.crafting.DefaultCraftingDisplay; +import net.minecraft.obfuscate.DontObfuscate; import net.minecraftforge.common.crafting.IShapedRecipe; -public class DefaultCraftingDisplayImpl { - public static void registerPlatformSizeProvider() { +public interface DefaultCraftingDisplayImpl { + @DontObfuscate + static void registerPlatformSizeProvider() { DefaultCraftingDisplay.registerSizeProvider(recipe -> { if (recipe instanceof IShapedRecipe) { return new CraftingRecipeSizeProvider.Size(((IShapedRecipe<?>) recipe).getRecipeWidth(), ((IShapedRecipe<?>) recipe).getRecipeHeight()); diff --git a/runtime/src/main/java/me/shedaniel/rei/impl/client/ClientHelperImpl.java b/runtime/src/main/java/me/shedaniel/rei/impl/client/ClientHelperImpl.java index 8acb6c09e..6b97c8514 100644 --- a/runtime/src/main/java/me/shedaniel/rei/impl/client/ClientHelperImpl.java +++ b/runtime/src/main/java/me/shedaniel/rei/impl/client/ClientHelperImpl.java @@ -227,7 +227,8 @@ public class ClientHelperImpl implements ClientHelper { Minecraft.getInstance().player.displayClientMessage(Component.translatable("text.rei.too_long_nbt"), false); } try { - Class.forName("me.shedaniel.rei.impl.client.%s.CommandSenderImpl".formatted(Platform.isForge() ? "forge" : "fabric")) + String s = "me.shedaniel.rei.impl.client.%s.CommandSenderImpl"; + Class.forName(s.contains("%s") ? s.formatted(Platform.isForge() ? "forge" : "fabric") : s) .getDeclaredMethod("sendCommand", String.class) .invoke(null, StringUtils.removeStart(madeUpCommand, "/")); } catch (IllegalAccessException | ClassNotFoundException | NoSuchMethodException | InvocationTargetException e) { diff --git a/runtime/src/main/java/me/shedaniel/rei/impl/client/gui/credits/CreditsScreen.java b/runtime/src/main/java/me/shedaniel/rei/impl/client/gui/credits/CreditsScreen.java index 830bcae36..13ba4db46 100644 --- a/runtime/src/main/java/me/shedaniel/rei/impl/client/gui/credits/CreditsScreen.java +++ b/runtime/src/main/java/me/shedaniel/rei/impl/client/gui/credits/CreditsScreen.java @@ -131,7 +131,8 @@ public class CreditsScreen extends Screen { private static void fillTranslators(Exception[] exception, List<Tuple<String, List<TranslatorEntry>>> translators) { try { - Class.forName("me.shedaniel.rei.impl.client.gui.credits.%s.CreditsScreenImpl".formatted(Platform.isForge() ? "forge" : "fabric")) + String s = "me.shedaniel.rei.impl.client.gui.credits.%s.CreditsScreenImpl"; + Class.forName(s.contains("%s") ? s.formatted(Platform.isForge() ? "forge" : "fabric") : s) .getDeclaredMethod("fillTranslators", Exception[].class, List.class) .invoke(null, exception, translators); } catch (IllegalAccessException | ClassNotFoundException | NoSuchMethodException | InvocationTargetException e) { diff --git a/runtime/src/main/java/me/shedaniel/rei/impl/common/plugins/PluginManagerImpl.java b/runtime/src/main/java/me/shedaniel/rei/impl/common/plugins/PluginManagerImpl.java index 1264b9abf..54342abdf 100644 --- a/runtime/src/main/java/me/shedaniel/rei/impl/common/plugins/PluginManagerImpl.java +++ b/runtime/src/main/java/me/shedaniel/rei/impl/common/plugins/PluginManagerImpl.java @@ -269,9 +269,21 @@ public class PluginManagerImpl<P extends REIPlugin<?>> implements PluginManager< } private static String name(Class<?> clazz) { - String simpleName = clazz.getSimpleName(); - if (simpleName.isEmpty()) return clazz.getName(); - return simpleName; + for (Class<?> anInterface : clazz.getInterfaces()) { + if (!anInterface.getName().startsWith("me.shedaniel.rei.impl")) { + return _name(anInterface); + } + } + + return _name(clazz); + } + + private static String _name(Class<?> clazz) { + String name = clazz.getName(); + if (name.contains(".")) { + name = name.substring(name.lastIndexOf(".") + 1); + } + return name.replace('$', '.'); } @Override diff --git a/settings.gradle b/settings.gradle index be97e596c..937a949bf 100755 --- a/settings.gradle +++ b/settings.gradle @@ -14,6 +14,3 @@ include "default-plugin" include "runtime" include "fabric" include "forge" - -include "jei-compatibility-layer" -include "jei-internals-workaround" |
