Cleanup some output and move the Jar-In-Jar extractor to before any coremods/mods are loaded so.

The intention is to rework this entire thing to use maven style storage, IF we can get Mojang to pass in the Libraries folder.
This commit is contained in:
LexManos 2017-08-08 20:13:05 -07:00
parent cc30c679e4
commit ee6805397f
3 changed files with 111 additions and 76 deletions

View File

@ -256,16 +256,9 @@ public class FMLModContainer implements ModContainer
} }
String mcVersionString = (String)descriptor.get("acceptedMinecraftVersions"); String mcVersionString = (String)descriptor.get("acceptedMinecraftVersions");
if ("[1.8.8]".equals(mcVersionString)) mcVersionString = "[1.8.8,1.8.9]"; // MC 1.8.8 and 1.8.9 is forward SRG compatible so accept these versions by default.
if ("[1.9.4]".equals(mcVersionString) ||
"[1.9,1.9.4]".equals(mcVersionString) ||
"[1.9.4,1.10)".equals(mcVersionString) ||
"[1.10]".equals(mcVersionString))
mcVersionString = "[1.9.4,1.10.2]";
if ("[1.11]".equals(mcVersionString))
mcVersionString = "[1.11,1.11.2]";
if ("[1.12]".equals(mcVersionString)) if ("[1.12]".equals(mcVersionString))
mcVersionString = "[1.12,1.12.1]"; mcVersionString = "[1.12,1.12.1]";
if (!Strings.isNullOrEmpty(mcVersionString)) if (!Strings.isNullOrEmpty(mcVersionString))
{ {
minecraftAccepted = VersionParser.parseRange(mcVersionString); minecraftAccepted = VersionParser.parseRange(mcVersionString);

View File

@ -42,6 +42,8 @@ import java.util.jar.Attributes;
import java.util.jar.JarEntry; import java.util.jar.JarEntry;
import java.util.jar.JarFile; import java.util.jar.JarFile;
import org.apache.commons.compress.utils.IOUtils;
import com.google.common.io.ByteStreams; import com.google.common.io.ByteStreams;
import com.google.common.io.Files; import com.google.common.io.Files;
import net.minecraft.launchwrapper.ITweaker; import net.minecraft.launchwrapper.ITweaker;
@ -254,43 +256,18 @@ public class CoreModManager {
} }
private static void discoverCoreMods(File mcDir, LaunchClassLoader classLoader) private static void findDerpMods(LaunchClassLoader classLoader, File modDir, File modDirVer)
{ {
ModListHelper.parseModList(mcDir); File[] derplist = listFiles((dir, name) -> name.endsWith(".jar.zip"), modDir, modDirVer);
FMLLog.log.debug("Discovering coremods");
File coreMods = setupCoreModDir(mcDir);
FilenameFilter ff = new FilenameFilter() {
@Override
public boolean accept(File dir, String name)
{
return name.endsWith(".jar");
}
};
FilenameFilter derpfilter = new FilenameFilter() {
@Override
public boolean accept(File dir, String name)
{
return name.endsWith(".jar.zip");
}
};
File[] derplist = coreMods.listFiles(derpfilter);
if (derplist != null && derplist.length > 0) if (derplist != null && derplist.length > 0)
{ {
FMLLog.log.fatal("FML has detected several badly downloaded jar files, which have been named as zip files. You probably need to download them again, or they may not work properly"); FMLLog.log.fatal("FML has detected several badly downloaded jar files, which have been named as zip files. You probably need to download them again, or they may not work properly");
for (File f : derplist) for (File f : derplist)
{
FMLLog.log.fatal("Problem file : {}", f.getName()); FMLLog.log.fatal("Problem file : {}", f.getName());
}
} }
FileFilter derpdirfilter = new FileFilter() {
@Override
public boolean accept(File pathname)
{
return pathname.isDirectory() && new File(pathname,"META-INF").isDirectory();
}
}; FileFilter derpdirfilter = pathname -> pathname.isDirectory() && new File(pathname,"META-INF").isDirectory();
File[] derpdirlist = coreMods.listFiles(derpdirfilter); File[] derpdirlist = listFiles(derpdirfilter, modDir, modDirVer);
if (derpdirlist != null && derpdirlist.length > 0) if (derpdirlist != null && derpdirlist.length > 0)
{ {
FMLLog.log.fatal("There appear to be jars extracted into the mods directory. This is VERY BAD and will almost NEVER WORK WELL"); FMLLog.log.fatal("There appear to be jars extracted into the mods directory. This is VERY BAD and will almost NEVER WORK WELL");
@ -304,11 +281,12 @@ public class CoreModManager {
RuntimeException re = new RuntimeException("Extracted mod jars found, loading will NOT continue"); RuntimeException re = new RuntimeException("Extracted mod jars found, loading will NOT continue");
// We're generating a crash report for the launcher to show to the user here // We're generating a crash report for the launcher to show to the user here
// Does this actually work with the obfed names?
try try
{ {
Class<?> crashreportclass = classLoader.loadClass("b"); Class<?> crashreportclass = classLoader.loadClass("b");
Object crashreport = crashreportclass.getMethod("a", Throwable.class, String.class).invoke(null, re, "FML has discovered extracted jar files in the mods directory.\nThis breaks mod loading functionality completely.\nRemove the directories and replace with the jar files originally provided."); Object crashreport = crashreportclass.getMethod("a", Throwable.class, String.class).invoke(null, re, "FML has discovered extracted jar files in the mods directory.\nThis breaks mod loading functionality completely.\nRemove the directories and replace with the jar files originally provided.");
File crashreportfile = new File(new File(coreMods.getParentFile(),"crash-reports"),String.format("fml-crash-%1$tY-%1$tm-%1$td_%1$tH.%1$tM.%1$tS.txt",Calendar.getInstance())); File crashreportfile = new File(new File(modDir.getParentFile(),"crash-reports"),String.format("fml-crash-%1$tY-%1$tm-%1$td_%1$tH.%1$tM.%1$tS.txt",Calendar.getInstance()));
crashreportclass.getMethod("a",File.class).invoke(crashreport, crashreportfile); crashreportclass.getMethod("a",File.class).invoke(crashreport, crashreportfile);
FMLLog.log.fatal("#@!@# FML has crashed the game deliberately. Crash report saved to: #@!@# {}", crashreportfile.getAbsolutePath()); FMLLog.log.fatal("#@!@# FML has crashed the game deliberately. Crash report saved to: #@!@# {}", crashreportfile.getAbsolutePath());
} catch (Exception e) } catch (Exception e)
@ -318,13 +296,51 @@ public class CoreModManager {
} }
throw re; throw re;
} }
File[] coreModList = coreMods.listFiles(ff); }
File versionedModDir = new File(coreMods, FMLInjectionData.mccversion);
if (versionedModDir.isDirectory()) private static File[] listFiles(FilenameFilter filter, File ... dirs)
{
File[] ret = null;
for (File dir : dirs)
{ {
File[] versionedCoreMods = versionedModDir.listFiles(ff); if (!dir.isDirectory() || !dir.exists())
coreModList = ObjectArrays.concat(coreModList, versionedCoreMods, File.class); continue;
if (ret == null)
ret = dir.listFiles(filter);
else
ret = ObjectArrays.concat(ret, dir.listFiles(filter), File.class);
} }
return ret;
}
private static File[] listFiles(FileFilter filter, File ... dirs)
{
File[] ret = null;
for (File dir : dirs)
{
if (!dir.isDirectory() || !dir.exists())
continue;
if (ret == null)
ret = dir.listFiles(filter);
else
ret = ObjectArrays.concat(ret, dir.listFiles(filter), File.class);
}
return ret;
}
private static void discoverCoreMods(File mcDir, LaunchClassLoader classLoader)
{
File modsDir = setupCoreModDir(mcDir);
File modsDirVer = new File(modsDir, FMLInjectionData.mccversion);
findDerpMods(classLoader, modsDir, modsDirVer);
extractPackedJars(modsDir, modsDirVer);
ModListHelper.parseModList(mcDir);
FMLLog.log.debug("Discovering coremods");
File[] coreModList = listFiles((dir, name) -> name.endsWith(".jar"), modsDir, modsDirVer);
coreModList = ObjectArrays.concat(coreModList, ModListHelper.additionalMods.values().toArray(new File[0]), File.class); coreModList = ObjectArrays.concat(coreModList, ModListHelper.additionalMods.values().toArray(new File[0]), File.class);
@ -371,7 +387,6 @@ public class CoreModManager {
ignoredModFiles.add(coreMod.getName()); ignoredModFiles.add(coreMod.getName());
continue; continue;
} }
ModListHelper.additionalMods.putAll(extractContainedDepJars(jar, coreMods, versionedModDir));
fmlCorePlugin = mfAttributes.getValue("FMLCorePlugin"); fmlCorePlugin = mfAttributes.getValue("FMLCorePlugin");
if (fmlCorePlugin == null) if (fmlCorePlugin == null)
{ {
@ -387,17 +402,7 @@ public class CoreModManager {
} }
finally finally
{ {
if (jar != null) IOUtils.closeQuietly(jar);
{
try
{
jar.close();
}
catch (IOException e)
{
// Noise
}
}
} }
// Support things that are mod jars, but not FML mod jars // Support things that are mod jars, but not FML mod jars
try try
@ -424,10 +429,43 @@ public class CoreModManager {
} }
} }
private static Map<String,File> extractContainedDepJars(JarFile jar, File baseModsDir, File versionedModsDir) throws IOException private static void extractPackedJars(File modsDir, File modsDirVer)
{ {
Map<String,File> result = Maps.newHashMap(); for (File dir : new File[]{modsDir, modsDirVer})
if (!jar.getManifest().getMainAttributes().containsKey(MODCONTAINSDEPS)) return result; {
for (File file : listFiles((d, name) -> name.endsWith(".jar"), dir))
{
JarFile jar = null;
Attributes mfAttributes;
try
{
jar = new JarFile(file);
if (jar.getManifest() == null)
continue;
mfAttributes = jar.getManifest().getMainAttributes();
String modSide = mfAttributes.containsKey(MODSIDE) ? mfAttributes.getValue(MODSIDE) : "BOTH";
if (! ("BOTH".equals(modSide) || FMLLaunchHandler.side.name().equals(modSide)))
continue;
extractContainedDepJars(jar, dir == modsDir ? modsDir : modsDirVer, dir == modsDir ? modsDirVer : modsDir);
}
catch (IOException ioe)
{
FMLLog.log.error("Unable to read the jar file {} - ignoring", file.getName(), ioe);
continue;
}
finally
{
IOUtils.closeQuietly(jar);
}
}
}
}
private static void extractContainedDepJars(JarFile jar, File ... modsDirs) throws IOException
{
if (!jar.getManifest().getMainAttributes().containsKey(MODCONTAINSDEPS)) return;
String deps = jar.getManifest().getMainAttributes().getValue(MODCONTAINSDEPS); String deps = jar.getManifest().getMainAttributes().getValue(MODCONTAINSDEPS);
String[] depList = deps.split(" "); String[] depList = deps.split(" ");
@ -445,21 +483,22 @@ public class CoreModManager {
FMLLog.log.error("Found invalid ContainsDeps declaration {} in {}", dep, jar.getName()); FMLLog.log.error("Found invalid ContainsDeps declaration {} in {}", dep, jar.getName());
continue; continue;
} }
File target = new File(versionedModsDir, depEndName);
File modTarget = new File(baseModsDir, depEndName);
if (target.exists())
{
FMLLog.log.debug("Found existing ContainsDep extracted to {}, skipping extraction", target.getCanonicalPath());
result.put(dep,target);
continue;
}
else if (modTarget.exists())
{
FMLLog.log.debug("Found ContainsDep in main mods directory at {}, skipping extraction", modTarget.getCanonicalPath());
result.put(dep, modTarget);
continue;
}
boolean exit = false;
for (File f : modsDirs)
{
File tmp = new File(f, depEndName);
if (tmp.exists())
{
FMLLog.log.debug("Found existing ContainsDep extracted to {}, skipping extraction", tmp.getCanonicalPath());
exit = true;
break;
}
}
if (exit)
continue;
File target = new File(modsDirs[0], depEndName);
FMLLog.log.debug("Extracting ContainedDep {} from {} to {}", dep, jar.getName(), target.getCanonicalPath()); FMLLog.log.debug("Extracting ContainedDep {} from {} to {}", dep, jar.getName(), target.getCanonicalPath());
try try
{ {
@ -471,13 +510,12 @@ public class CoreModManager {
ByteStreams.copy(jarInputStream, targetOutputStream); ByteStreams.copy(jarInputStream, targetOutputStream);
} }
FMLLog.log.debug("Extracted ContainedDep {} from {} to {}", dep, jar.getName(), target.getCanonicalPath()); FMLLog.log.debug("Extracted ContainedDep {} from {} to {}", dep, jar.getName(), target.getCanonicalPath());
result.put(dep,target);
} catch (IOException e) } catch (IOException e)
{ {
FMLLog.log.error("An error occurred extracting dependency", e); FMLLog.log.error("An error occurred extracting dependency", e);
} }
} }
return result; return;
} }
private static Method ADDURL; private static Method ADDURL;
@ -749,4 +787,5 @@ public class CoreModManager {
builder.append("Contact their authors BEFORE contacting forge\n\n"); builder.append("Contact their authors BEFORE contacting forge\n\n");
} }
} }
} }

View File

@ -88,8 +88,11 @@ public class FMLLaunchHandler
FMLLog.log.info("Forge Mod Loader version {}.{}.{}.{} for Minecraft {} loading", FMLInjectionData.major, FMLInjectionData.minor, FMLLog.log.info("Forge Mod Loader version {}.{}.{}.{} for Minecraft {} loading", FMLInjectionData.major, FMLInjectionData.minor,
FMLInjectionData.rev, FMLInjectionData.build, FMLInjectionData.mccversion); FMLInjectionData.rev, FMLInjectionData.build, FMLInjectionData.mccversion);
FMLLog.log.info("Java is {}, version {}, running on {}:{}:{}, installed at {}", System.getProperty("java.vm.name"), System.getProperty("java.version"), System.getProperty("os.name"), System.getProperty("os.arch"), System.getProperty("os.version"), System.getProperty("java.home")); FMLLog.log.info("Java is {}, version {}, running on {}:{}:{}, installed at {}", System.getProperty("java.vm.name"), System.getProperty("java.version"), System.getProperty("os.name"), System.getProperty("os.arch"), System.getProperty("os.version"), System.getProperty("java.home"));
FMLLog.log.debug("Java classpath at launch is {}", System.getProperty("java.class.path")); FMLLog.log.debug("Java classpath at launch is:");
FMLLog.log.debug("Java library path at launch is {}", System.getProperty("java.library.path")); for (String path : System.getProperty("java.class.path").split(File.pathSeparator))
FMLLog.log.debug(" {}", path);
FMLLog.log.debug("Java library path at launch is:");
for (String path : System.getProperty("java.library.path").split(File.pathSeparator))
try try
{ {