diff --git a/.gitignore b/.gitignore index 5e3be19d7..1de565933 100644 --- a/.gitignore +++ b/.gitignore @@ -1,2 +1 @@ -target -src/main/java/de/bixilon/minosoft/Config.java \ No newline at end of file +target \ No newline at end of file diff --git a/pom.xml b/pom.xml index 43fcf58fb..3b5814651 100644 --- a/pom.xml +++ b/pom.xml @@ -32,6 +32,11 @@ json 20180813 + + org.yaml + snakeyaml + 1.25 + \ No newline at end of file diff --git a/src/main/java/de/bixilon/minosoft/Config.java b/src/main/java/de/bixilon/minosoft/Config.java index 60df37037..91a514fda 100644 --- a/src/main/java/de/bixilon/minosoft/Config.java +++ b/src/main/java/de/bixilon/minosoft/Config.java @@ -1,6 +1,5 @@ package de.bixilon.minosoft; public class Config { - public static String username = ""; // mojang email - public static String password = ""; + public static String homeDir; } diff --git a/src/main/java/de/bixilon/minosoft/Minosoft.java b/src/main/java/de/bixilon/minosoft/Minosoft.java index b688aea1a..2f2c39d4a 100644 --- a/src/main/java/de/bixilon/minosoft/Minosoft.java +++ b/src/main/java/de/bixilon/minosoft/Minosoft.java @@ -1,12 +1,57 @@ package de.bixilon.minosoft; +import de.bixilon.minosoft.config.Configuration; +import de.bixilon.minosoft.config.GameConfiguration; import de.bixilon.minosoft.logging.Log; +import de.bixilon.minosoft.objects.Account; +import de.bixilon.minosoft.objects.Player; import de.bixilon.minosoft.protocol.network.Connection; +import de.bixilon.minosoft.util.OSUtil; + +import java.io.File; +import java.io.IOException; public class Minosoft { + static Configuration config; + public static void main(String[] args) { Log.info("Starting..."); - Connection c = new Connection("127.0.0.1", 25565); + setConfigFolder(); + Log.info("Reading config file..."); + try { + config = new Configuration("game.yml"); + } catch (IOException e) { + Log.fatal("Failed to load config file!"); + e.printStackTrace(); + return; + } + Log.info(String.format("Loaded config file (version=%s)", config.getInteger(GameConfiguration.CONFIG_VERSION))); + Connection c = new Connection(config.getString("debug.host"), config.getInteger("debug.port")); + c.setPlayer(new Player(new Account(config.getString("debug.username"), config.getString("debug.password")))); c.connect(); } + + /** + * Sets Config.homeDir to the correct folder per OS + */ + public static void setConfigFolder() { + String folder = System.getProperty("user.home"); + if (!folder.endsWith(File.separator)) { + folder += "/"; + } + switch (OSUtil.getOS()) { + case LINUX: + folder += ".local/share/minosoft/"; + break; + case WINDOWS: + Config.homeDir = "AppData/Roaming/Minosoft/"; + break; + //ToDo: Mac, Other + } + Config.homeDir = folder; + } + + public static Configuration getConfig() { + return config; + } } diff --git a/src/main/java/de/bixilon/minosoft/config/ConfigEnum.java b/src/main/java/de/bixilon/minosoft/config/ConfigEnum.java new file mode 100644 index 000000000..19bbf9cd6 --- /dev/null +++ b/src/main/java/de/bixilon/minosoft/config/ConfigEnum.java @@ -0,0 +1,5 @@ +package de.bixilon.minosoft.config; + +public interface ConfigEnum { + public String getPath(); +} diff --git a/src/main/java/de/bixilon/minosoft/config/Configuration.java b/src/main/java/de/bixilon/minosoft/config/Configuration.java new file mode 100644 index 000000000..b3092fa30 --- /dev/null +++ b/src/main/java/de/bixilon/minosoft/config/Configuration.java @@ -0,0 +1,72 @@ +package de.bixilon.minosoft.config; + +import de.bixilon.minosoft.Config; +import org.yaml.snakeyaml.Yaml; + +import java.io.*; +import java.nio.file.Files; +import java.nio.file.Paths; +import java.util.LinkedHashMap; + +public class Configuration { + LinkedHashMap config; + + public Configuration(String filename) throws IOException { + + File file = new File(Config.homeDir + "config/" + filename); + if (!file.exists()) { + // no configuration file + InputStream input = getClass().getResourceAsStream("/config/" + filename); + if (input == null) { + throw new FileNotFoundException(String.format("[Config] Missing default config: %s!", filename)); + } + File c_folder = new File(Config.homeDir + "config/"); + if (!c_folder.exists() && !c_folder.mkdirs()) { + throw new IOException("[Config] Could not create config folder!"); + } + Files.copy(input, Paths.get(file.getAbsolutePath())); + file = new File(Config.homeDir + "config/" + filename); + } + Yaml yml = new Yaml(); + config = yml.load(new FileInputStream(file)); + } + + public boolean getBoolean(String path) { + return (boolean) get(path); + } + + public boolean getBoolean(ConfigEnum config) { + return getBoolean(config.getPath()); + } + + public int getInteger(String path) { + return (int) get(path); + } + + public int getInteger(ConfigEnum config) { + return getInteger(config.getPath()); + } + + public String getString(String path) { + return (String) get(path); + } + + public String getString(ConfigEnum config) { + return getString(config.getPath()); + } + + + public Object get(String path) { + if (path.contains(".")) { + // split + String[] spilt = path.split("\\."); + LinkedHashMap temp = config; + for (int i = 0; i < spilt.length - 1; i++) { + temp = (LinkedHashMap) temp.get(spilt[i]); + } + return temp.get(spilt[spilt.length - 1]); + } + return config.get(path); + } +} + diff --git a/src/main/java/de/bixilon/minosoft/config/GameConfiguration.java b/src/main/java/de/bixilon/minosoft/config/GameConfiguration.java new file mode 100644 index 000000000..9e0a55ab9 --- /dev/null +++ b/src/main/java/de/bixilon/minosoft/config/GameConfiguration.java @@ -0,0 +1,19 @@ +package de.bixilon.minosoft.config; + +public enum GameConfiguration implements ConfigEnum { + CONFIG_VERSION("version"), + GAME_RENDER_DISTANCE("game.render-distance"), + NETWORK_FAKE_CLIENT_BRAND("network.fake-client-brand"); + + + String path; + + GameConfiguration(String path) { + this.path = path; + } + + @Override + public String getPath() { + return path; + } +} diff --git a/src/main/java/de/bixilon/minosoft/protocol/network/Connection.java b/src/main/java/de/bixilon/minosoft/protocol/network/Connection.java index ae569dd4c..306f66a59 100644 --- a/src/main/java/de/bixilon/minosoft/protocol/network/Connection.java +++ b/src/main/java/de/bixilon/minosoft/protocol/network/Connection.java @@ -1,8 +1,6 @@ package de.bixilon.minosoft.protocol.network; -import de.bixilon.minosoft.Config; import de.bixilon.minosoft.logging.Log; -import de.bixilon.minosoft.objects.Account; import de.bixilon.minosoft.objects.Player; import de.bixilon.minosoft.protocol.packets.ClientboundPacket; import de.bixilon.minosoft.protocol.packets.ServerboundPacket; @@ -23,7 +21,7 @@ public class Connection { private final Network network; private final PacketHandler handler; private final ArrayList handlingQueue; - private Player player = new Player(new Account(Config.username, Config.password)); + private Player player; private ConnectionState state = ConnectionState.DISCONNECTED; private boolean onlyPing; @@ -133,4 +131,8 @@ public class Connection { }); handleThread.start(); } + + public void setPlayer(Player player) { + this.player = player; + } } diff --git a/src/main/java/de/bixilon/minosoft/protocol/packets/serverbound/play/PacketPluginMessageSending.java b/src/main/java/de/bixilon/minosoft/protocol/packets/serverbound/play/PacketPluginMessageSending.java index 056518f34..c7c21a205 100644 --- a/src/main/java/de/bixilon/minosoft/protocol/packets/serverbound/play/PacketPluginMessageSending.java +++ b/src/main/java/de/bixilon/minosoft/protocol/packets/serverbound/play/PacketPluginMessageSending.java @@ -16,6 +16,11 @@ public class PacketPluginMessageSending implements ServerboundPacket { this.data = data; } + public PacketPluginMessageSending(String channel, String data) { + this.channel = channel; + this.data = data.getBytes(); + } + @Override public OutPacketBuffer write(ProtocolVersion v) { diff --git a/src/main/java/de/bixilon/minosoft/protocol/protocol/PacketHandler.java b/src/main/java/de/bixilon/minosoft/protocol/protocol/PacketHandler.java index f3e25a121..f879dbba9 100644 --- a/src/main/java/de/bixilon/minosoft/protocol/protocol/PacketHandler.java +++ b/src/main/java/de/bixilon/minosoft/protocol/protocol/PacketHandler.java @@ -1,5 +1,7 @@ package de.bixilon.minosoft.protocol.protocol; +import de.bixilon.minosoft.Minosoft; +import de.bixilon.minosoft.config.GameConfiguration; import de.bixilon.minosoft.logging.Log; import de.bixilon.minosoft.protocol.network.Connection; import de.bixilon.minosoft.protocol.packets.clientbound.login.PacketEncryptionKeyRequest; @@ -87,8 +89,7 @@ public class PacketHandler { Log.info(String.format("Server is running %s on version %s", new String(pkg.getData()), connection.getVersion().getName())); // send back own brand - // ToDo option to toggle for minosoft or original minecraft - connection.sendPacket(new PacketPluginMessageSending("MC|Brand", "Minosoft".getBytes())); + connection.sendPacket(new PacketPluginMessageSending("MC|Brand", (Minosoft.getConfig().getBoolean(GameConfiguration.NETWORK_FAKE_CLIENT_BRAND) ? "vanilla" : "Minosoft"))); } } diff --git a/src/main/java/de/bixilon/minosoft/util/OSUtil.java b/src/main/java/de/bixilon/minosoft/util/OSUtil.java new file mode 100644 index 000000000..3da6b4033 --- /dev/null +++ b/src/main/java/de/bixilon/minosoft/util/OSUtil.java @@ -0,0 +1,29 @@ +package de.bixilon.minosoft.util; + +public final class OSUtil { + private static OS os; + + public static OS getOS() { + if (os == null) { + String name = System.getProperty("os.name"); + if (name.startsWith("Windows")) { + os = OS.WINDOWS; + } else if (name.startsWith("Linux")) { + os = OS.LINUX; + } else if (name.startsWith("Mac")) { + os = OS.MAC; + } else { + os = OS.OTHER; + } + } + return os; + } + + public enum OS { + WINDOWS, + LINUX, + MAC, + OTHER + } + +} diff --git a/src/main/resources/config/game.yml b/src/main/resources/config/game.yml new file mode 100644 index 000000000..d555389c8 --- /dev/null +++ b/src/main/resources/config/game.yml @@ -0,0 +1,16 @@ +# Settings of the game +version: 1 # do not edit this, used for migration between versions of config + +# game +game: + render-distance: 12 + +network: + fake-client-brand: false # if true, minosoft will tell the server that this is unmodified vanilla. if false, it will tell "minosoft". + +# this will be removed soon +debug: + host: "127.0.0.1" + port: 25565 + username: "Player" + password: "secret123" \ No newline at end of file