Skip to content

Commit

Permalink
Add 'ASM' classes from the old blood moon mod
Browse files Browse the repository at this point in the history
  • Loading branch information
OldSerpskiStalker committed Nov 1, 2024
1 parent f85cb06 commit d96b386
Show file tree
Hide file tree
Showing 2 changed files with 191 additions and 0 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,152 @@
package org.imesense.dynamicspawncontrol.technical.asmclasstransformer;

import java.util.Iterator;
import net.minecraft.launchwrapper.IClassTransformer;
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.objectweb.asm.ClassReader;
import org.objectweb.asm.ClassWriter;
import org.objectweb.asm.tree.AbstractInsnNode;
import org.objectweb.asm.tree.ClassNode;
import org.objectweb.asm.tree.FieldInsnNode;
import org.objectweb.asm.tree.InsnList;
import org.objectweb.asm.tree.InsnNode;
import org.objectweb.asm.tree.MethodInsnNode;
import org.objectweb.asm.tree.MethodNode;
import org.objectweb.asm.tree.VarInsnNode;

public final class ClassTransformerBloodMoon implements IClassTransformer
{
Logger logger = LogManager.getLogger("Bloodmoon");

public byte[] transform(String name, String transformedName, byte[] basicClass) {
if (transformedName.equals("net.minecraft.client.renderer.EntityRenderer")) {
return this.patchEntityRendererClass(basicClass);
} else {
return transformedName.equals("net.minecraft.world.World") ? this.patchWorld(basicClass) : basicClass;
}
}

private byte[] patchWorld(byte[] basicClass) {
ClassNode classNode = new ClassNode();
ClassReader classReader = new ClassReader(basicClass);
classReader.accept(classNode, 0);
this.logger.log(Level.DEBUG, "Found World Class: " + classNode.name);
MethodNode getSkyColor = null;
MethodNode getMoonPhase = null;
Iterator var6 = classNode.methods.iterator();

while(var6.hasNext()) {
MethodNode mn = (MethodNode)var6.next();
if (mn.name.equals(MCPNames.method("func_72833_a"))) {
getSkyColor = mn;
} else if (mn.name.equals(MCPNames.method("func_72853_d"))) {
getMoonPhase = mn;
}
}

InsnList toInsert;
int i;
AbstractInsnNode ain;
if (getSkyColor != null) {
this.logger.log(Level.DEBUG, " - Found getSkyColor");

for(i = 0; i < getSkyColor.instructions.size(); ++i) {
ain = getSkyColor.instructions.get(i);
if (ain.getOpcode() == 176) {
toInsert = new InsnList();
toInsert.add(new FieldInsnNode(178, "lumien/bloodmoon/client/ClientBloodmoonHandler", "INSTANCE", "Llumien/bloodmoon/client/ClientBloodmoonHandler;"));
toInsert.add(new InsnNode(95));
toInsert.add(new MethodInsnNode(182, "lumien/bloodmoon/client/ClientBloodmoonHandler", "skyColorHook", "(Lnet/minecraft/util/math/Vec3d;)Lnet/minecraft/util/math/Vec3d;", false));
i += 3;
getSkyColor.instructions.insertBefore(ain, toInsert);
}
}
}

if (getMoonPhase != null) {
this.logger.log(Level.DEBUG, " - Found getMoonPhase");

for(i = 0; i < getMoonPhase.instructions.size(); ++i) {
ain = getMoonPhase.instructions.get(i);
if (ain.getOpcode() == 172) {
toInsert = new InsnList();
toInsert.add(new FieldInsnNode(178, "lumien/bloodmoon/client/ClientBloodmoonHandler", "INSTANCE", "Llumien/bloodmoon/client/ClientBloodmoonHandler;"));
toInsert.add(new MethodInsnNode(182, "lumien/bloodmoon/client/ClientBloodmoonHandler", "moonColorHook", "()V", false));
i += 2;
getMoonPhase.instructions.insertBefore(ain, toInsert);
}
}
}

ClassWriter writer = new ClassWriter(3);
classNode.accept(writer);
return writer.toByteArray();
}

private byte[] patchEntityRendererClass(byte[] basicClass) {
ClassNode classNode = new ClassNode();
ClassReader classReader = new ClassReader(basicClass);
classReader.accept(classNode, 0);
this.logger.log(Level.DEBUG, "Found EntityRenderer Class: " + classNode.name);
String methodName = MCPNames.method("func_78472_g");
MethodNode updateLightmap = null;
Iterator var6 = classNode.methods.iterator();

while(var6.hasNext()) {
MethodNode mn = (MethodNode)var6.next();
if (mn.name.equals(methodName)) {
updateLightmap = mn;
}
}

if (updateLightmap != null) {
this.logger.log(Level.DEBUG, " - Found updateLightmap");
boolean insertedHook = false;

for(int i = 0; i < updateLightmap.instructions.size(); ++i) {
AbstractInsnNode an = updateLightmap.instructions.get(i);
if (an instanceof VarInsnNode && !insertedHook) {
VarInsnNode iin = (VarInsnNode)an;
if (iin.getOpcode() == 54 && iin.var == 23) {
InsnList toInsert = new InsnList();
toInsert.add(new FieldInsnNode(178, "lumien/bloodmoon/client/ClientBloodmoonHandler", "INSTANCE", "Llumien/bloodmoon/client/ClientBloodmoonHandler;"));
toInsert.add(new VarInsnNode(21, 5));
toInsert.add(new VarInsnNode(21, 21));
toInsert.add(new MethodInsnNode(182, "lumien/bloodmoon/client/ClientBloodmoonHandler", "manipulateRed", "(II)I", false));
toInsert.add(new VarInsnNode(54, 21));
toInsert.add(new FieldInsnNode(178, "lumien/bloodmoon/client/ClientBloodmoonHandler", "INSTANCE", "Llumien/bloodmoon/client/ClientBloodmoonHandler;"));
toInsert.add(new VarInsnNode(21, 5));
toInsert.add(new VarInsnNode(21, 22));
toInsert.add(new MethodInsnNode(182, "lumien/bloodmoon/client/ClientBloodmoonHandler", "manipulateGreen", "(II)I", false));
toInsert.add(new VarInsnNode(54, 22));
toInsert.add(new FieldInsnNode(178, "lumien/bloodmoon/client/ClientBloodmoonHandler", "INSTANCE", "Llumien/bloodmoon/client/ClientBloodmoonHandler;"));
toInsert.add(new VarInsnNode(21, 5));
toInsert.add(new VarInsnNode(21, 23));
toInsert.add(new MethodInsnNode(182, "lumien/bloodmoon/client/ClientBloodmoonHandler", "manipulateBlue", "(II)I", false));
toInsert.add(new VarInsnNode(54, 23));
updateLightmap.instructions.insert(iin, toInsert);
insertedHook = true;
}
}
}
}

ClassWriter writer = new ClassWriter(1);
classNode.accept(writer);
return writer.toByteArray();
}

private byte[] patchDummyClass(byte[] basicClass) {
ClassNode classNode = new ClassNode();
ClassReader classReader = new ClassReader(basicClass);
classReader.accept(classNode, 0);
this.logger.log(Level.INFO, "Found Dummy Class: " + classNode.name);
ClassWriter writer = new ClassWriter(3);
classNode.accept(writer);
return writer.toByteArray();
}
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
package org.imesense.dynamicspawncontrol.technical.plugin;

import net.minecraftforge.common.ForgeVersion;
import net.minecraftforge.fml.relauncher.IFMLLoadingPlugin;
import org.imesense.dynamicspawncontrol.ProjectStructure;
import org.imesense.dynamicspawncontrol.technical.asmclasstransformer.ClassTransformerBloodMoon;

import java.util.Map;

@IFMLLoadingPlugin.MCVersion(ForgeVersion.mcVersion)
@IFMLLoadingPlugin.Name(ProjectStructure.STRUCT_INFO_MOD.MOD_ID)
@IFMLLoadingPlugin.SortingIndex(LoadingPluginBloodMoon.AFTER_DEOBF)
public final class LoadingPluginBloodMoon implements IFMLLoadingPlugin
{
public static boolean IN_MCP = false;

public static final int AFTER_DEOBF = 1002;

public String[] getASMTransformerClass() {
return new String[]{ClassTransformerBloodMoon.class.getName()};
}

public String getModContainerClass() {
return null;
}

public String getSetupClass() {
return null;
}

public void injectData(Map<String, Object> data) {
IN_MCP = !(Boolean)data.get("runtimeDeobfuscationEnabled");
}

public String getAccessTransformerClass() {
return null;
}
}

0 comments on commit d96b386

Please sign in to comment.