diff --git a/LaunchServer/src/main/java/ru/gravit/launchserver/LaunchServer.java b/LaunchServer/src/main/java/ru/gravit/launchserver/LaunchServer.java index d8022245..247f7a88 100644 --- a/LaunchServer/src/main/java/ru/gravit/launchserver/LaunchServer.java +++ b/LaunchServer/src/main/java/ru/gravit/launchserver/LaunchServer.java @@ -31,6 +31,7 @@ import ru.gravit.launcher.Launcher; import ru.gravit.launcher.LauncherAPI; +import ru.gravit.launcher.hasher.FileNameMatcher; import ru.gravit.launcher.hasher.HashedDir; import ru.gravit.utils.helper.CommonHelper; import ru.gravit.utils.helper.IOHelper; diff --git a/LaunchServer/src/main/java/ru/gravit/launchserver/response/update/UpdateListResponse.java b/LaunchServer/src/main/java/ru/gravit/launchserver/response/update/UpdateListResponse.java index e9314ab3..06f19a61 100644 --- a/LaunchServer/src/main/java/ru/gravit/launchserver/response/update/UpdateListResponse.java +++ b/LaunchServer/src/main/java/ru/gravit/launchserver/response/update/UpdateListResponse.java @@ -1,11 +1,13 @@ package ru.gravit.launchserver.response.update; +import java.util.ArrayList; import java.util.Map.Entry; import java.util.Set; import ru.gravit.launcher.hasher.HashedDir; import ru.gravit.launcher.serialize.HInput; import ru.gravit.launcher.serialize.HOutput; +import ru.gravit.launcher.serialize.config.entry.ListConfigEntry; import ru.gravit.launcher.serialize.signed.SignedObjectHolder; import ru.gravit.launchserver.LaunchServer; import ru.gravit.launchserver.response.Response; @@ -19,10 +21,9 @@ public UpdateListResponse(LaunchServer server, long session, HInput input, HOutp @Override public void reply() throws Exception { Set>> updateDirs = server.getUpdateDirs(); - // Write all update dirs names output.writeLength(updateDirs.size(), 0); for (Entry> entry : updateDirs) - output.writeString(entry.getKey(), 255); + output.writeString(entry.getKey(), 255); } } diff --git a/Launcher/src/main/java/ru/gravit/launcher/request/update/UpdateRequest.java b/Launcher/src/main/java/ru/gravit/launcher/request/update/UpdateRequest.java index 6cb02bd3..46a75724 100644 --- a/Launcher/src/main/java/ru/gravit/launcher/request/update/UpdateRequest.java +++ b/Launcher/src/main/java/ru/gravit/launcher/request/update/UpdateRequest.java @@ -18,6 +18,7 @@ import ru.gravit.launcher.LauncherAPI; import ru.gravit.launcher.LauncherConfig; +import ru.gravit.launcher.client.ClientLauncher; import ru.gravit.launcher.hasher.FileNameMatcher; import ru.gravit.launcher.hasher.HashedDir; import ru.gravit.launcher.hasher.HashedEntry; @@ -305,7 +306,9 @@ protected SignedObjectHolder requestDo(HInput input, HOutput output) // Get diff between local and remote dir SignedObjectHolder remoteHDirHolder = new SignedObjectHolder<>(input, config.publicKey, HashedDir::new); - HashedDir.Diff diff = remoteHDirHolder.object.diff(localDir, matcher); + HashedDir hackHackedDir = remoteHDirHolder.object; + ClientLauncher.profile.pushOptional(hackHackedDir,!ClientLauncher.profile.isUpdateFastCheck()); + HashedDir.Diff diff = hackHackedDir.diff(localDir, matcher); totalSize = diff.mismatch.size(); boolean compress = input.readBoolean(); diff --git a/libLauncher/src/main/java/ru/gravit/launcher/hasher/HashedDir.java b/libLauncher/src/main/java/ru/gravit/launcher/hasher/HashedDir.java index 01a425f4..97c8a13f 100644 --- a/libLauncher/src/main/java/ru/gravit/launcher/hasher/HashedDir.java +++ b/libLauncher/src/main/java/ru/gravit/launcher/hasher/HashedDir.java @@ -147,7 +147,14 @@ public Diff diff(HashedDir other, FileNameMatcher matcher) { HashedDir extra = other.sideDiff(this, matcher, new LinkedList<>(), false); return new Diff(mismatch, extra); } - + public void pushHashedFile(String name, HashedFile file) + { + map.put(name,file); + } + public void remove(String name) + { + map.remove(name); + } @LauncherAPI public HashedEntry getEntry(String name) { return map.get(name); diff --git a/libLauncher/src/main/java/ru/gravit/launcher/profiles/ClientProfile.java b/libLauncher/src/main/java/ru/gravit/launcher/profiles/ClientProfile.java index 8eafe103..f8134c00 100644 --- a/libLauncher/src/main/java/ru/gravit/launcher/profiles/ClientProfile.java +++ b/libLauncher/src/main/java/ru/gravit/launcher/profiles/ClientProfile.java @@ -1,12 +1,19 @@ package ru.gravit.launcher.profiles; +import java.io.File; import java.io.IOException; import java.net.InetSocketAddress; +import java.nio.file.Path; +import java.nio.file.Paths; +import java.util.ArrayList; import java.util.HashMap; +import java.util.List; import java.util.Map; import ru.gravit.launcher.LauncherAPI; import ru.gravit.launcher.hasher.FileNameMatcher; +import ru.gravit.launcher.hasher.HashedDir; +import ru.gravit.launcher.hasher.HashedFile; import ru.gravit.utils.helper.IOHelper; import ru.gravit.utils.helper.VerifyHelper; import ru.gravit.launcher.serialize.HInput; @@ -75,9 +82,11 @@ public String toString() { private final IntegerConfigEntry serverPort; // Updater and client watch service - private final ListConfigEntry update; - private final ListConfigEntry updateExclusions; - private final ListConfigEntry updateVerify; + private final List update = new ArrayList<>(); + private final List updateExclusions = new ArrayList<>(); + private final List updateVerify = new ArrayList<>(); + private final List updateOptional = new ArrayList<>(); + private final List markUpdateOptional = new ArrayList<>(); private final BooleanConfigEntry updateFastCheck; private final BooleanConfigEntry useWhitelist; @@ -104,9 +113,10 @@ public ClientProfile(BlockConfigEntry block) { serverPort = block.getEntry("serverPort", IntegerConfigEntry.class); // Updater and client watch service - update = block.getEntry("update", ListConfigEntry.class); - updateVerify = block.getEntry("updateVerify", ListConfigEntry.class); - updateExclusions = block.getEntry("updateExclusions", ListConfigEntry.class); + block.getEntry("update", ListConfigEntry.class).stream(StringConfigEntry.class).forEach(update::add); + block.getEntry("updateVerify", ListConfigEntry.class).stream(StringConfigEntry.class).forEach(updateVerify::add); + block.getEntry("updateOptional", ListConfigEntry.class).stream(StringConfigEntry.class).forEach(updateOptional::add); + block.getEntry("updateExclusions", ListConfigEntry.class).stream(StringConfigEntry.class).forEach(updateExclusions::add); updateFastCheck = block.getEntry("updateFastCheck", BooleanConfigEntry.class); useWhitelist = block.getEntry("useWhitelist", BooleanConfigEntry.class); @@ -149,10 +159,19 @@ public String[] getClientArgs() { } @LauncherAPI - public FileNameMatcher getClientUpdateMatcher() { - String[] updateArray = update.stream(StringConfigEntry.class).toArray(String[]::new); - String[] verifyArray = updateVerify.stream(StringConfigEntry.class).toArray(String[]::new); - String[] exclusionsArray = updateExclusions.stream(StringConfigEntry.class).toArray(String[]::new); + public FileNameMatcher getClientUpdateMatcher(/*boolean excludeOptional*/) { + String[] updateArray = update.toArray(new String[0]); + String[] verifyArray = updateVerify.toArray(new String[0]); + List excludeList; + //if(excludeOptional) + //{ + // excludeList = new ArrayList<>(); + // excludeList.addAll(updateExclusions); + // excludeList.addAll(updateOptional); + //} + //else + excludeList = updateExclusions; + String[] exclusionsArray = excludeList.toArray(new String[0]); return new FileNameMatcher(updateArray, verifyArray, exclusionsArray); } @@ -171,6 +190,30 @@ public String getServerAddress() { return serverAddress.getValue(); } + @LauncherAPI + public void markOptional(String opt) + { + if(!updateOptional.contains(opt)) throw new SecurityException(String.format("Optional mod %s not found in optionalList",opt)); + markUpdateOptional.add(opt); + } + @LauncherAPI + public void unmarkOptional(String opt) + { + if(!updateOptional.contains(opt)) throw new SecurityException(String.format("Optional mod %s not found in optionalList",opt)); + markUpdateOptional.remove(opt); + } + public void pushOptional(HashedDir dir,boolean digest) throws IOException { + for(String opt : updateOptional) + { + dir.remove(opt); + } + for(String opt : markUpdateOptional) + { + Path path = Paths.get(opt); + File file = new File(path.toAbsolutePath().toString()); + dir.pushHashedFile(opt, new HashedFile(path,file.getUsableSpace(),digest)); + } + } @LauncherAPI public int getServerPort() { return serverPort.getValue(); @@ -233,11 +276,6 @@ public void verify() { VerifyHelper.verify(getServerAddress(), VerifyHelper.NOT_EMPTY, "Server address can't be empty"); VerifyHelper.verifyInt(getServerPort(), VerifyHelper.range(0, 65535), "Illegal server port: " + getServerPort()); - // Updater and client watch service - update.verifyOfType(ConfigEntry.Type.STRING); - updateVerify.verifyOfType(ConfigEntry.Type.STRING); - updateExclusions.verifyOfType(ConfigEntry.Type.STRING); - // Client launcher jvmArgs.verifyOfType(ConfigEntry.Type.STRING); classPath.verifyOfType(ConfigEntry.Type.STRING);