mirror of
https://github.com/MinecraftForge/MinecraftForge.git
synced 2026-11-12 16:27:47 +00:00
client and server work standalone and in forge dev. Next up userdev.
Moved some launchplugin code to the launcher. Moved servermain to the launcher. server currently needs cmdline arguments --fml.forgeVersion=24.0.51-1.13-pre --fml.mcVersion=1.13 --fml.mcpVersion=2018.09.12.04.11.00 --fml.forgeGroup=net.minecraftforge.test
This commit is contained in:
1 parent
e9580877b4
commit
6baddc7e26
19 files changed
+71
-34
No files matched your search
@@ -26,6 +26,7 @@ import net.minecraftforge.fml.common.event.FMLServerStartingEvent;
|
||||
import net.minecraftforge.fml.javafmlmod.FMLModLoadingContext;
|
||||
import net.minecraftforge.server.command.ForgeCommand;
|
||||
import net.minecraftforge.versions.forge.ForgeVersion;
|
||||
import net.minecraftforge.versions.mcp.MCPVersion;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
|
||||
@@ -73,6 +74,7 @@ public class ForgeMod implements WorldPersistenceHooks.WorldPersistenceHook
|
||||
|
||||
public ForgeMod()
|
||||
{
|
||||
LOGGER.info("Forge mod loading, version {}, for MC {} with MCP {}", ForgeVersion.getVersion(), MCPVersion.getMCVersion(), MCPVersion.getMCPVersion());
|
||||
INSTANCE = this;
|
||||
WorldPersistenceHooks.addHook(this);
|
||||
WorldPersistenceHooks.addHook(new FMLWorldPersistenceHook());
|
||||
@@ -82,6 +84,7 @@ public class ForgeMod implements WorldPersistenceHooks.WorldPersistenceHook
|
||||
MinecraftForge.EVENT_BUS.addListener(this::serverStarting);
|
||||
MinecraftForge.EVENT_BUS.addListener(this::playerLogin);
|
||||
MinecraftForge.EVENT_BUS.addListener(this::serverStopping);
|
||||
ForgeConfig.load();
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
@@ -1,73 +0,0 @@
|
||||
/*
|
||||
* Minecraft Forge
|
||||
* Copyright (c) 2016-2018.
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation version 2.1
|
||||
* of the License.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
package net.minecraftforge.common.asm;
|
||||
|
||||
import java.nio.file.Path;
|
||||
import java.util.List;
|
||||
|
||||
import org.objectweb.asm.Opcodes;
|
||||
import org.objectweb.asm.Type;
|
||||
import org.objectweb.asm.tree.AnnotationNode;
|
||||
import org.objectweb.asm.tree.ClassNode;
|
||||
import cpw.mods.modlauncher.serviceapi.ILaunchPluginService;
|
||||
|
||||
/**
|
||||
* Removes the final modifier from fields with the @CapabilityInject annotation, prevents the JITer from in lining them so our runtime replacements can work.
|
||||
*/
|
||||
public class CapabilityInjectDefinalize implements ILaunchPluginService {
|
||||
|
||||
private final String CAP = "Lnet/minecraftforge/common/capabilities/Capability;"; //Don't directly reference this to prevent class loading.
|
||||
private final String CAP_INJECT = "Lnet/minecraftforge/common/capabilities/CapabilityInject;"; //Don't directly reference this to prevent class loading.
|
||||
|
||||
@Override
|
||||
public String name() {
|
||||
return "capability_inject_definalize";
|
||||
}
|
||||
|
||||
@Override public void addResource(Path resource, String name) { }
|
||||
|
||||
@Override public <T> T getExtension() { return null; } // ?
|
||||
|
||||
@Override
|
||||
public boolean handlesClass(Type classType, boolean isEmpty)
|
||||
{
|
||||
return !isEmpty; //Check for annotations?
|
||||
}
|
||||
|
||||
private boolean hasHolder(List<AnnotationNode> lst)
|
||||
{
|
||||
return lst != null && lst.stream().anyMatch(n -> n.desc.equals(CAP_INJECT));
|
||||
}
|
||||
|
||||
@Override
|
||||
public ClassNode processClass(ClassNode classNode, Type classType)
|
||||
{
|
||||
final int flags = Opcodes.ACC_PUBLIC | Opcodes.ACC_STATIC | Opcodes.ACC_FINAL;
|
||||
|
||||
classNode.fields.stream().filter(f -> ((f.access & flags) == flags) && f.desc.equals(CAP) && hasHolder(f.visibleAnnotations)).forEach(f ->
|
||||
{
|
||||
f.access &= ~Opcodes.ACC_FINAL; //Strip final
|
||||
f.access |= Opcodes.ACC_SYNTHETIC; //Add Synthetic so we can check in runtime.
|
||||
});
|
||||
|
||||
return classNode;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,106 +0,0 @@
|
||||
/*
|
||||
* Minecraft Forge
|
||||
* Copyright (c) 2016-2018.
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation version 2.1
|
||||
* of the License.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
package net.minecraftforge.common.asm;
|
||||
|
||||
import java.nio.file.Path;
|
||||
import java.util.List;
|
||||
|
||||
import org.objectweb.asm.Opcodes;
|
||||
import org.objectweb.asm.Type;
|
||||
import org.objectweb.asm.tree.AnnotationNode;
|
||||
import org.objectweb.asm.tree.ClassNode;
|
||||
import cpw.mods.modlauncher.serviceapi.ILaunchPluginService;
|
||||
|
||||
/**
|
||||
* Removes the final modifier from fields with the @ObjectHolder annotation, prevents the JITer from in lining them so our runtime replacements can work.
|
||||
* Will also de-finalize all fields in on class level annotations.
|
||||
*/
|
||||
public class ObjectHolderDefinalize implements ILaunchPluginService {
|
||||
|
||||
private final String OBJECT_HOLDER = "Lnet/minecraftforge/registries/ObjectHolder;"; //Don't directly reference this to prevent class loading.
|
||||
|
||||
@Override
|
||||
public String name() {
|
||||
return "object_holder_definalize";
|
||||
}
|
||||
|
||||
@Override public void addResource(Path resource, String name) { }
|
||||
|
||||
@Override public <T> T getExtension() { return null; } // ?
|
||||
|
||||
@Override
|
||||
public boolean handlesClass(Type classType, boolean isEmpty)
|
||||
{
|
||||
return !isEmpty; //Check for annotations?
|
||||
}
|
||||
|
||||
private boolean hasHolder(List<AnnotationNode> lst)
|
||||
{
|
||||
return lst != null && lst.stream().anyMatch(n -> n.desc.equals(OBJECT_HOLDER));
|
||||
}
|
||||
|
||||
private String getValue(List<AnnotationNode> lst)
|
||||
{
|
||||
AnnotationNode ann = lst.stream().filter(n -> n.desc.equals(OBJECT_HOLDER)).findFirst().get();
|
||||
if (ann.values != null)
|
||||
{
|
||||
for (int x = 0; x < ann.values.size() - 1; x += 2) {
|
||||
if (ann.values.get(x).equals("value")) {
|
||||
return (String)ann.values.get(x + 1);
|
||||
}
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ClassNode processClass(ClassNode classNode, Type classType)
|
||||
{
|
||||
//Must be public static finals, and non-array objects
|
||||
final int flags = Opcodes.ACC_PUBLIC | Opcodes.ACC_STATIC | Opcodes.ACC_FINAL;
|
||||
|
||||
//Fix Annotated Fields before injecting from class level
|
||||
classNode.fields.stream().filter(f -> ((f.access & flags) == flags) && f.desc.startsWith("L") && hasHolder(f.visibleAnnotations)).forEach(f ->
|
||||
{
|
||||
f.access &= ~Opcodes.ACC_FINAL; //Strip final
|
||||
f.access |= Opcodes.ACC_SYNTHETIC; //Add Synthetic so we can check in runtime. ? Good idea?
|
||||
});
|
||||
|
||||
if (hasHolder(classNode.visibleAnnotations)) //Class level, de-finalize all fields and add @ObjectHolder to them!
|
||||
{
|
||||
@SuppressWarnings("unused")
|
||||
String value = getValue(classNode.visibleAnnotations);
|
||||
classNode.fields.stream().filter(f -> ((f.access & flags) == flags) && f.desc.startsWith("L")).forEach(f ->
|
||||
{
|
||||
f.access &= ~Opcodes.ACC_FINAL;
|
||||
f.access |= Opcodes.ACC_SYNTHETIC;
|
||||
/*if (!hasHolder(f.visibleAnnotations)) //Add field level annotation, doesn't do anything until after we figure out how ASMDataTable is gatherered
|
||||
{
|
||||
if (value == null)
|
||||
f.visitAnnotation(OBJECT_HOLDER, true);
|
||||
else
|
||||
f.visitAnnotation(OBJECT_HOLDER, true).visit("value", value + ":" + f.name.toLowerCase());
|
||||
}*/
|
||||
});
|
||||
}
|
||||
return classNode;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,193 +0,0 @@
|
||||
/*
|
||||
* Minecraft Forge
|
||||
* Copyright (c) 2016-2018.
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation version 2.1
|
||||
* of the License.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
package net.minecraftforge.common.asm;
|
||||
|
||||
import java.nio.file.Path;
|
||||
|
||||
import net.minecraftforge.fml.AdvancedLogMessageAdapter;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
import org.objectweb.asm.Label;
|
||||
import org.objectweb.asm.Opcodes;
|
||||
import org.objectweb.asm.Type;
|
||||
import org.objectweb.asm.commons.InstructionAdapter;
|
||||
import org.objectweb.asm.tree.ClassNode;
|
||||
import org.objectweb.asm.tree.FieldNode;
|
||||
import org.objectweb.asm.tree.MethodNode;
|
||||
|
||||
import cpw.mods.modlauncher.serviceapi.ILaunchPluginService;
|
||||
|
||||
/**
|
||||
* Modifies specified enums to allow runtime extension by making the $VALUES field non-final and
|
||||
* injecting constructor calls which are not valid in normal java code.
|
||||
*/
|
||||
public class RuntimeEnumExtender implements ILaunchPluginService {
|
||||
|
||||
private static final Logger LOGGER = LogManager.getLogger();
|
||||
private final Type STRING = Type.getType(String.class);
|
||||
private final Type ENUM = Type.getType(Enum.class);
|
||||
private final Type ARRAY_UTILS = Type.getType("Lorg/apache/commons/lang3/ArrayUtils;"); //Don't directly reference this to prevent class loading.
|
||||
private final String ADD_DESC = Type.getMethodDescriptor(Type.getType(Object[].class), Type.getType(Object[].class), Type.getType(Object.class));
|
||||
private final Type ENUM_HELPER = Type.getType("Lnet/minecraftforge/common/util/EnumHelper;"); //Again, not direct reference to prevent class loading.
|
||||
private final String CLEAN_DESC = Type.getMethodDescriptor(Type.VOID_TYPE, Type.getType(Class.class));
|
||||
private final String NAME_DESC = Type.getMethodDescriptor(STRING);
|
||||
private final String EQUALS_DESC = Type.getMethodDescriptor(Type.BOOLEAN_TYPE, STRING);
|
||||
|
||||
@Override
|
||||
public String name() {
|
||||
return "runtime_enum_extender";
|
||||
}
|
||||
|
||||
@Override public void addResource(Path resource, String name) { }
|
||||
|
||||
@Override public <T> T getExtension() { return null; } // ?
|
||||
|
||||
@Override
|
||||
public boolean handlesClass(Type classType, boolean isEmpty)
|
||||
{
|
||||
return !isEmpty; //Any way to determine if its a enum at this level?
|
||||
}
|
||||
|
||||
@Override
|
||||
public ClassNode processClass(ClassNode classNode, Type classType)
|
||||
{
|
||||
if ((classNode.access & Opcodes.ACC_ENUM) == 0)
|
||||
return classNode;
|
||||
|
||||
Type array = Type.getType("[" + classType.getDescriptor());
|
||||
final int flags = Opcodes.ACC_PRIVATE | Opcodes.ACC_STATIC | Opcodes.ACC_FINAL | Opcodes.ACC_SYNTHETIC;
|
||||
|
||||
FieldNode values = classNode.fields.stream().filter(f -> f.desc.contentEquals(array.getDescriptor()) && ((f.access & flags) == flags)).findFirst().orElse(null);
|
||||
//Static methods named "create", with first argument as a string, and returning this type
|
||||
classNode.methods.stream().filter(m -> ((m.access & Opcodes.ACC_STATIC) != 0) && m.name.equals("create") && Type.getReturnType(m.desc).equals(classType)).forEach(mtd ->
|
||||
{
|
||||
Type[] args = Type.getArgumentTypes(mtd.desc);
|
||||
if (args.length == 0 || !args[0].equals(STRING))
|
||||
return;
|
||||
|
||||
Type[] ctrArgs = new Type[args.length + 1];
|
||||
ctrArgs[0] = STRING;
|
||||
ctrArgs[1] = Type.INT_TYPE;
|
||||
for (int x = 1; x < args.length; x++)
|
||||
ctrArgs[1 + x] = args[x];
|
||||
|
||||
String desc = Type.getMethodDescriptor(Type.VOID_TYPE, ctrArgs);
|
||||
|
||||
MethodNode ctr = classNode.methods.stream().filter(m -> m.name.equals("<init>") && m.desc.equals(desc)).findFirst().orElse(null);
|
||||
if (ctr == null)
|
||||
{
|
||||
LOGGER.error(()->new AdvancedLogMessageAdapter(sb-> {
|
||||
sb.append("Enum has create method with no matching constructor:\n");
|
||||
sb.append(" Enum: " + classType.getDescriptor()).append("\n");
|
||||
sb.append(" Target: ").append(desc).append("\n");
|
||||
classNode.methods.stream().filter(m -> m.name.equals("<init>")).forEach(m -> sb.append(" : ").append(m.desc).append("\n"));
|
||||
}));
|
||||
throw new IllegalStateException("Enum has create method with no matching constructor: " + desc);
|
||||
}
|
||||
|
||||
if (values == null)
|
||||
{
|
||||
LOGGER.error(()->new AdvancedLogMessageAdapter(sb-> {
|
||||
sb.append("Enum has create method but we could not find $VALUES. Found:\n");
|
||||
classNode.fields.stream().filter(f -> (f.access & Opcodes.ACC_STATIC) != 0).
|
||||
forEach(m -> sb.append(" ").append(m.name).append(" ").append(m.desc).append("\n"));
|
||||
}));
|
||||
throw new IllegalStateException("Enum has create method but we could not find $VALUES");
|
||||
}
|
||||
|
||||
values.access &= values.access & ~Opcodes.ACC_FINAL; //Strip the final so JITer doesn't inline things.
|
||||
|
||||
mtd.instructions.clear();
|
||||
InstructionAdapter ins = new InstructionAdapter(mtd);
|
||||
|
||||
int vars = 0;
|
||||
for (Type arg : args)
|
||||
vars += arg.getSize();
|
||||
|
||||
{
|
||||
vars += 1; //int x
|
||||
Label for_start = new Label();
|
||||
Label for_condition = new Label();
|
||||
Label for_inc = new Label();
|
||||
|
||||
ins.iconst(0);
|
||||
ins.store(vars, Type.INT_TYPE);
|
||||
ins.goTo(for_condition);
|
||||
//if (!VALUES[x].name().equalsIgnoreCase(name)) goto for_inc
|
||||
ins.mark(for_start);
|
||||
ins.getstatic(classType.getInternalName(), values.name, values.desc);
|
||||
ins.load(vars, Type.INT_TYPE);
|
||||
ins.aload(array);
|
||||
ins.invokevirtual(ENUM.getInternalName(), "name", NAME_DESC, false);
|
||||
ins.load(0, STRING);
|
||||
ins.invokevirtual(STRING.getInternalName(), "equalsIgnoreCase", EQUALS_DESC, false);
|
||||
ins.ifeq(for_inc);
|
||||
//return VALUES[x];
|
||||
ins.getstatic(classType.getInternalName(), values.name, values.desc);
|
||||
ins.load(vars, Type.INT_TYPE);
|
||||
ins.aload(array);
|
||||
ins.areturn(classType);
|
||||
//x++
|
||||
ins.mark(for_inc);
|
||||
ins.iinc(vars, 1);
|
||||
//if (x < VALUES.length) goto for_start
|
||||
ins.mark(for_condition);
|
||||
ins.load(vars, Type.INT_TYPE);
|
||||
ins.getstatic(classType.getInternalName(), values.name, values.desc);
|
||||
ins.arraylength();
|
||||
ins.ificmplt(for_start);
|
||||
}
|
||||
|
||||
{
|
||||
vars += 1; //enum ret;
|
||||
//ret = new ThisType(name, VALUES.length + 1, args..)
|
||||
ins.anew(classType);
|
||||
ins.dup();
|
||||
ins.load(0, STRING);
|
||||
ins.getstatic(classType.getInternalName(), values.name, values.desc);
|
||||
ins.arraylength();
|
||||
ins.iconst(1);
|
||||
ins.add(Type.INT_TYPE);
|
||||
int idx = 1;
|
||||
for (int x = 1; x < args.length; x++)
|
||||
{
|
||||
ins.load(idx, args[x]);
|
||||
idx += args[x].getSize();
|
||||
}
|
||||
ins.invokespecial(classType.getInternalName(), "<init>", desc, false);
|
||||
ins.store(vars, classType);
|
||||
// VALUES = ArrayUtils.add(VALUES, ret)
|
||||
ins.getstatic(classType.getInternalName(), values.name, values.desc);
|
||||
ins.load(vars, classType);
|
||||
ins.invokestatic(ARRAY_UTILS.getInternalName(), "add", ADD_DESC, false);
|
||||
ins.checkcast(array);
|
||||
ins.putstatic(classType.getInternalName(), values.name, values.desc);
|
||||
//EnumHelper.cleanEnumCache(ThisType.class)
|
||||
ins.visitLdcInsn(classType);
|
||||
ins.invokestatic(ENUM_HELPER.getInternalName(), "cleanEnumCache", CLEAN_DESC, false);
|
||||
//return ret
|
||||
ins.load(vars, classType);
|
||||
ins.areturn(classType);
|
||||
}
|
||||
});
|
||||
return classNode;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,60 +0,0 @@
|
||||
/*
|
||||
* Minecraft Forge
|
||||
* Copyright (c) 2016-2018.
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation version 2.1
|
||||
* of the License.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
package net.minecraftforge.fml;
|
||||
|
||||
import org.apache.logging.log4j.message.Message;
|
||||
import org.apache.logging.log4j.util.StringBuilderFormattable;
|
||||
|
||||
import java.util.function.Consumer;
|
||||
|
||||
public class AdvancedLogMessageAdapter implements Message, StringBuilderFormattable {
|
||||
private static final Object[] EMPTY = new Object[0];
|
||||
|
||||
private final Consumer<StringBuilder> logMessageBuilder;
|
||||
|
||||
public AdvancedLogMessageAdapter(final Consumer<StringBuilder> logMessageBuilder) {
|
||||
this.logMessageBuilder = logMessageBuilder;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getFormattedMessage() {
|
||||
return "";
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getFormat() {
|
||||
return "";
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object[] getParameters() {
|
||||
return EMPTY;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Throwable getThrowable() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void formatTo(final StringBuilder buffer) {
|
||||
logMessageBuilder.accept(buffer);
|
||||
}
|
||||
}
|
||||
@@ -74,7 +74,9 @@ public class LaunchTesting
|
||||
"--fml.mcVersion", "1.13");
|
||||
} else if (Objects.equals(target, "fmldevserver")) {
|
||||
String[] launchargs = ObjectArrays.concat(new String[] {"--launchTarget", target,
|
||||
"--gameDir", "."}, args, String.class);
|
||||
"--gameDir", ".", "--fml.forgeVersion", "24.0.0",
|
||||
"--fml.mcpVersion", "2018.11.30",
|
||||
"--fml.mcVersion", "1.13"}, args, String.class);
|
||||
Launcher.main(launchargs);
|
||||
}
|
||||
Thread.sleep(10000);
|
||||
|
||||
@@ -51,6 +51,7 @@ public class FMLModContainer extends ModContainer
|
||||
public FMLModContainer(IModInfo info, String className, ClassLoader modClassLoader, ModFileScanData modFileScanResults)
|
||||
{
|
||||
super(info);
|
||||
LOGGER.debug("Creating FMLModContainer instance for {} with classLoader {} & {}", className, modClassLoader, getClass().getClassLoader());
|
||||
this.scanResults = modFileScanResults;
|
||||
triggerMap.put(ModLoadingStage.CONSTRUCT, dummy().andThen(this::beforeEvent).andThen(this::constructMod).andThen(this::afterEvent));
|
||||
triggerMap.put(ModLoadingStage.PREINIT, dummy().andThen(this::beforeEvent).andThen(this::preinitMod).andThen(this::fireEvent).andThen(this::afterEvent));
|
||||
|
||||
@@ -46,6 +46,7 @@ import java.util.jar.Manifest;
|
||||
import java.util.zip.ZipEntry;
|
||||
import java.util.zip.ZipInputStream;
|
||||
|
||||
import net.minecraftforge.versions.mcp.MCPVersion;
|
||||
import org.apache.commons.lang3.tuple.Pair;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
@@ -86,7 +87,7 @@ public class LibraryManager
|
||||
libraries_dir = Repository.get("libraries");
|
||||
|
||||
File mods = new File(minecraftHome, "mods");
|
||||
File mods_ver = new File(mods, ForgeVersion.mcVersion);
|
||||
File mods_ver = new File(mods, MCPVersion.getMCVersion());
|
||||
|
||||
ModList memory = null;
|
||||
if (!ENABLE_AUTO_MOD_MOVEMENT)
|
||||
@@ -471,7 +472,7 @@ public class LibraryManager
|
||||
}
|
||||
}
|
||||
|
||||
for (String dir : new String[]{"mods", "mods" + File.separatorChar + ForgeVersion.mcVersion})
|
||||
for (String dir : new String[]{"mods", "mods" + File.separatorChar + MCPVersion.getMCVersion()})
|
||||
{
|
||||
File base = new File(mcDir, dir);
|
||||
if (!base.isDirectory() || !base.exists())
|
||||
|
||||
@@ -30,6 +30,7 @@ import java.util.Map;
|
||||
import java.util.Optional;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import net.minecraftforge.versions.mcp.MCPVersion;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
|
||||
@@ -66,7 +67,7 @@ public class ModList
|
||||
@SuppressWarnings("unchecked")
|
||||
public static List<ModList> getKnownLists(File mcdir)
|
||||
{
|
||||
for (String list : new String[] {"mods/mod_list.json", "mods/" + ForgeVersion.mcVersion + "/mod_list.json"/* , TODO Launch args ((Map<String, String>)Launch.blackboard.get("launchArgs")).get("--modListFile")*/})
|
||||
for (String list : new String[] {"mods/mod_list.json", "mods/" + MCPVersion.getMCVersion() + "/mod_list.json"/* , TODO Launch args ((Map<String, String>)Launch.blackboard.get("launchArgs")).get("--modListFile")*/})
|
||||
{
|
||||
if (list != null)
|
||||
{
|
||||
@@ -87,7 +88,7 @@ public class ModList
|
||||
if (memory != null)
|
||||
lst.add(memory);
|
||||
|
||||
for (String list : new String[] {"mods/mod_list.json", "mods/" + ForgeVersion.mcVersion + "/mod_list.json"/* TODO Launch args, ((Map<String, String>)Launch.blackboard.get("launchArgs")).get("--modListFile")*/})
|
||||
for (String list : new String[] {"mods/mod_list.json", "mods/" + MCPVersion.getMCVersion() + "/mod_list.json"/* TODO Launch args, ((Map<String, String>)Launch.blackboard.get("launchArgs")).get("--modListFile")*/})
|
||||
{
|
||||
if (list != null)
|
||||
{
|
||||
|
||||
@@ -1,30 +0,0 @@
|
||||
/*
|
||||
* Minecraft Forge
|
||||
* Copyright (c) 2016-2018.
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Lesser General Public
|
||||
* License as published by the Free Software Foundation version 2.1
|
||||
* of the License.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this library; if not, write to the Free Software
|
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
package net.minecraftforge.server;
|
||||
|
||||
import com.google.common.collect.ObjectArrays;
|
||||
import cpw.mods.modlauncher.Launcher;
|
||||
|
||||
public class ServerMain {
|
||||
public static void main(String[] args) {
|
||||
final String[] argArray = ObjectArrays.concat(new String[]{"--launchTarget", "fmlserver","--gameDir", "."}, args, String.class);
|
||||
Launcher.main(argArray);
|
||||
}
|
||||
}
|
||||
@@ -20,6 +20,7 @@
|
||||
package net.minecraftforge.versions.forge;
|
||||
|
||||
import net.minecraftforge.fml.VersionChecker;
|
||||
import net.minecraftforge.fml.loading.JarVersionLookupHandler;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
|
||||
@@ -32,30 +33,18 @@ public class ForgeVersion
|
||||
private static final Logger LOGGER = LogManager.getLogger();
|
||||
// This is Forge's Mod Id, used for the ForgeMod and resource locations
|
||||
public static final String MOD_ID = "forge";
|
||||
// This is the minecraft version we're building for - used in various places in Forge/FML code
|
||||
public static final String mcVersion = "1.13";
|
||||
// This is the MCP data version we're using
|
||||
public static final String mcpVersion = "9.42";
|
||||
|
||||
private static final String forgeVersion;
|
||||
private static final String forgeSpec;
|
||||
private static final String forgeGroup;
|
||||
|
||||
static {
|
||||
String vers = ForgeVersion.class.getPackage().getImplementationVersion();
|
||||
if (vers == null) {
|
||||
vers = System.getProperty("forge.version");
|
||||
}
|
||||
LOGGER.debug(CORE, "Forge Version package {} from {}", ForgeVersion.class.getPackage(), ForgeVersion.class.getClassLoader());
|
||||
String vers = JarVersionLookupHandler.getImplementationVersion(ForgeVersion.class).orElse(System.getProperty("forge.version"));
|
||||
if (vers == null) throw new RuntimeException("Missing forge version, cannot continue");
|
||||
String spec = ForgeVersion.class.getPackage().getSpecificationVersion();
|
||||
if (spec == null) {
|
||||
spec = System.getProperty("forge.spec");
|
||||
}
|
||||
String spec = JarVersionLookupHandler.getSpecificationVersion(ForgeVersion.class).orElse(System.getProperty("forge.spec"));
|
||||
if (spec == null) throw new RuntimeException("Missing forge spec, cannot continue");
|
||||
String group = ForgeVersion.class.getPackage().getImplementationTitle();
|
||||
if (group == null) {
|
||||
group = System.getProperty("forge.group");
|
||||
}
|
||||
String group = JarVersionLookupHandler.getImplementationTitle(ForgeVersion.class).orElse(System.getProperty("forge.group"));
|
||||
if (group == null) {
|
||||
group = "net.minecraftforge"; // If all else fails, Our normal group
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user