diff options
Diffstat (limited to 'src/main/java')
49 files changed, 1856 insertions, 697 deletions
diff --git a/src/main/java/net/minecraft/server/BlockSkull.java b/src/main/java/net/minecraft/server/BlockSkull.java index e24b7408..b05f4639 100644 --- a/src/main/java/net/minecraft/server/BlockSkull.java +++ b/src/main/java/net/minecraft/server/BlockSkull.java @@ -84,9 +84,12 @@ public class BlockSkull extends BlockContainer { ItemStack itemstack = new ItemStack(Items.SKULL, 1, this.getDropData(world, i, j, k)); TileEntitySkull tileentityskull = (TileEntitySkull) world.getTileEntity(i, j, k); - if (tileentityskull.getSkullType() == 3 && tileentityskull.getExtraType() != null && tileentityskull.getExtraType().length() > 0) { + if (tileentityskull.getSkullType() == 3 && tileentityskull.getGameProfile() != null) { itemstack.setTag(new NBTTagCompound()); - itemstack.getTag().setString("SkullOwner", tileentityskull.getExtraType()); + NBTTagCompound nbttagcompound = new NBTTagCompound(); + + GameProfileSerializer.a(nbttagcompound, tileentityskull.getGameProfile()); + itemstack.getTag().set("SkullOwner", nbttagcompound); } this.a(world, i, j, k, itemstack); @@ -112,9 +115,12 @@ public class BlockSkull extends BlockContainer { ItemStack itemstack = new ItemStack(Items.SKULL, 1, this.getDropData(world, i, j, k)); TileEntitySkull tileentityskull = (TileEntitySkull) world.getTileEntity(i, j, k); - if (tileentityskull.getSkullType() == 3 && tileentityskull.getExtraType() != null && tileentityskull.getExtraType().length() > 0) { + if (tileentityskull.getSkullType() == 3 && tileentityskull.getGameProfile() != null) { itemstack.setTag(new NBTTagCompound()); - itemstack.getTag().setString("SkullOwner", tileentityskull.getExtraType()); + NBTTagCompound nbttagcompound = new NBTTagCompound(); + + GameProfileSerializer.a(nbttagcompound, tileentityskull.getGameProfile()); + itemstack.getTag().set("SkullOwner", nbttagcompound); } this.a(world, i, j, k, itemstack); diff --git a/src/main/java/net/minecraft/server/ChunkProviderServer.java b/src/main/java/net/minecraft/server/ChunkProviderServer.java index 5b3c821b..1b22934d 100644 --- a/src/main/java/net/minecraft/server/ChunkProviderServer.java +++ b/src/main/java/net/minecraft/server/ChunkProviderServer.java @@ -8,6 +8,7 @@ import java.util.List; import java.util.Set; import java.util.concurrent.ConcurrentHashMap; +import net.minecraft.util.com.google.common.collect.Lists; import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.Logger; @@ -317,12 +318,15 @@ public class ChunkProviderServer implements IChunkProvider { ChunkUnloadEvent event = new ChunkUnloadEvent(chunk.bukkitChunk); server.getPluginManager().callEvent(event); if (!event.isCancelled()) { - chunk.removeEntities(); - this.saveChunk(chunk); - this.saveChunkNOP(chunk); + if (chunk != null) { + chunk.removeEntities(); + this.saveChunk(chunk); + this.saveChunkNOP(chunk); + this.chunks.remove(chunkcoordinates); // CraftBukkit + } + // this.unloadQueue.remove(olong); // this.chunks.remove(olong.longValue()); - this.chunks.remove(chunkcoordinates); // CraftBukkit } } // CraftBukkit end diff --git a/src/main/java/net/minecraft/server/ChunkRegionLoader.java b/src/main/java/net/minecraft/server/ChunkRegionLoader.java index a3b75208..26bafe0a 100644 --- a/src/main/java/net/minecraft/server/ChunkRegionLoader.java +++ b/src/main/java/net/minecraft/server/ChunkRegionLoader.java @@ -1,6 +1,5 @@ package net.minecraft.server; -import java.io.DataInput; import java.io.DataInputStream; import java.io.DataOutput; import java.io.DataOutputStream; @@ -81,7 +80,7 @@ public class ChunkRegionLoader implements IChunkLoader, IAsyncChunkSaver { return null; } - nbttagcompound = NBTCompressedStreamTools.a((DataInput) datainputstream); + nbttagcompound = NBTCompressedStreamTools.a(datainputstream); } return this.a(world, i, j, nbttagcompound); diff --git a/src/main/java/net/minecraft/server/DedicatedServer.java b/src/main/java/net/minecraft/server/DedicatedServer.java index 1b05fbf4..9cef53fa 100644 --- a/src/main/java/net/minecraft/server/DedicatedServer.java +++ b/src/main/java/net/minecraft/server/DedicatedServer.java @@ -23,14 +23,14 @@ import org.bukkit.event.server.ServerCommandEvent; public class DedicatedServer extends MinecraftServer implements IMinecraftServer { - private static final Logger h = LogManager.getLogger(); - private final List i = Collections.synchronizedList(new ArrayList()); - private RemoteStatusListener j; - private RemoteControlListener k; + private static final Logger i = LogManager.getLogger(); + private final List j = Collections.synchronizedList(new ArrayList()); + private RemoteStatusListener k; + private RemoteControlListener l; public PropertyManager propertyManager; // CraftBukkit - private -> public private boolean generateStructures; - private EnumGamemode n; - private boolean o; + private EnumGamemode o; + private boolean p; // CraftBukkit start - Signature changed public DedicatedServer(joptsimple.OptionSet options) { @@ -67,14 +67,14 @@ public class DedicatedServer extends MinecraftServer implements IMinecraftServer System.setErr(new PrintStream(new LoggerOutputStream(logger, Level.WARN), true)); // CraftBukkit end - h.info("Starting minecraft server version 1.7.5"); + i.info("Starting minecraft server version 1.7.8"); if (Runtime.getRuntime().maxMemory() / 1024L / 1024L < 512L) { - h.warn("To start the server with more ram, launch it as \"java -Xmx1024M -Xms1024M -jar minecraft_server.jar\""); + i.warn("To start the server with more ram, launch it as \"java -Xmx1024M -Xms1024M -jar minecraft_server.jar\""); } - h.info("Loading properties"); + i.info("Loading properties"); this.propertyManager = new PropertyManager(this.options); // CraftBukkit - CLI argument support - if (this.M()) { + if (this.N()) { this.c("127.0.0.1"); } else { this.setOnlineMode(this.propertyManager.getBoolean("online-mode", true)); @@ -96,112 +96,122 @@ public class DedicatedServer extends MinecraftServer implements IMinecraftServer } this.generateStructures = this.propertyManager.getBoolean("generate-structures", true); - int i = this.propertyManager.getInt("gamemode", EnumGamemode.SURVIVAL.a()); + int gamemode = this.propertyManager.getInt("gamemode", EnumGamemode.SURVIVAL.a()); // CraftBukkit - Unique name to avoid stomping on logger - this.n = WorldSettings.a(i); - h.info("Default game type: " + this.n); + this.o = WorldSettings.a(gamemode); // CraftBukkit - Use new name + i.info("Default game type: " + this.o); InetAddress inetaddress = null; if (this.getServerIp().length() > 0) { inetaddress = InetAddress.getByName(this.getServerIp()); } - if (this.K() < 0) { + if (this.L() < 0) { this.setPort(this.propertyManager.getInt("server-port", 25565)); } - h.info("Generating keypair"); + i.info("Generating keypair"); this.a(MinecraftEncryption.b()); - h.info("Starting Minecraft server on " + (this.getServerIp().length() == 0 ? "*" : this.getServerIp()) + ":" + this.K()); + i.info("Starting Minecraft server on " + (this.getServerIp().length() == 0 ? "*" : this.getServerIp()) + ":" + this.L()); try { - this.ah().a(inetaddress, this.K()); + this.ai().a(inetaddress, this.L()); } catch (Throwable ioexception) { // CraftBukkit - IOException -> Throwable - h.warn("**** FAILED TO BIND TO PORT!"); - h.warn("The exception was: {}", new Object[] { ioexception.toString()}); - h.warn("Perhaps a server is already running on that port?"); + i.warn("**** FAILED TO BIND TO PORT!"); + i.warn("The exception was: {}", new Object[] { ioexception.toString()}); + i.warn("Perhaps a server is already running on that port?"); return false; } this.a((PlayerList) (new DedicatedPlayerList(this))); // CraftBukkit if (!this.getOnlineMode()) { - h.warn("**** SERVER IS RUNNING IN OFFLINE/INSECURE MODE!"); - h.warn("The server will make no attempt to authenticate usernames. Beware."); - h.warn("While this makes the game possible to play without internet access, it also opens up the ability for hackers to connect with any username they choose."); - h.warn("To change this, set \"online-mode\" to \"true\" in the server.properties file."); + i.warn("**** SERVER IS RUNNING IN OFFLINE/INSECURE MODE!"); + i.warn("The server will make no attempt to authenticate usernames. Beware."); + i.warn("While this makes the game possible to play without internet access, it also opens up the ability for hackers to connect with any username they choose."); + i.warn("To change this, set \"online-mode\" to \"true\" in the server.properties file."); } - // this.a((PlayerList) (new DedicatedPlayerList(this))); // CraftBukkit - moved up - this.convertable = new WorldLoaderServer(server.getWorldContainer()); // CraftBukkit - moved from MinecraftServer constructor - long j = System.nanoTime(); - - if (this.N() == null) { - this.k(this.propertyManager.getString("level-name", "world")); + if (this.aE()) { + this.getUserCache().c(); } - String s = this.propertyManager.getString("level-seed", ""); - String s1 = this.propertyManager.getString("level-type", "DEFAULT"); - String s2 = this.propertyManager.getString("generator-settings", ""); - long k = (new Random()).nextLong(); + if (!NameReferencingFileConverter.a(this.propertyManager)) { + return false; + } else { + // this.a((PlayerList) (new DedicatedPlayerList(this))); // CraftBukkit - moved up + this.convertable = new WorldLoaderServer(server.getWorldContainer()); // CraftBukkit - moved from MinecraftServer constructor + long j = System.nanoTime(); - if (s.length() > 0) { - try { - long l = Long.parseLong(s); + if (this.O() == null) { + this.k(this.propertyManager.getString("level-name", "world")); + } + + String s = this.propertyManager.getString("level-seed", ""); + String s1 = this.propertyManager.getString("level-type", "DEFAULT"); + String s2 = this.propertyManager.getString("generator-settings", ""); + long k = (new Random()).nextLong(); + + if (s.length() > 0) { + try { + long l = Long.parseLong(s); - if (l != 0L) { - k = l; + if (l != 0L) { + k = l; + } + } catch (NumberFormatException numberformatexception) { + k = (long) s.hashCode(); } - } catch (NumberFormatException numberformatexception) { - k = (long) s.hashCode(); } - } - WorldType worldtype = WorldType.getType(s1); + WorldType worldtype = WorldType.getType(s1); - if (worldtype == null) { - worldtype = WorldType.NORMAL; - } + if (worldtype == null) { + worldtype = WorldType.NORMAL; + } - this.as(); - this.getEnableCommandBlock(); - this.l(); - this.getSnooperEnabled(); - this.c(this.propertyManager.getInt("max-build-height", 256)); - this.c((this.getMaxBuildHeight() + 8) / 16 * 16); - this.c(MathHelper.a(this.getMaxBuildHeight(), 64, 256)); - this.propertyManager.a("max-build-height", Integer.valueOf(this.getMaxBuildHeight())); - h.info("Preparing level \"" + this.M() + "\""); - this.a(this.N(), this.N(), k, worldtype, s2); - long i1 = System.nanoTime() - j; - String s3 = String.format("%.3fs", new Object[] { Double.valueOf((double) i1 / 1.0E9D)}); - - h.info("Done (" + s3 + ")! For help, type \"help\" or \"?\""); - if (this.propertyManager.getBoolean("enable-query", false)) { - h.info("Starting GS4 status listener"); - this.j = new RemoteStatusListener(this); - this.j.a(); - } + this.at(); + this.getEnableCommandBlock(); + this.l(); + this.getSnooperEnabled(); + this.c(this.propertyManager.getInt("max-build-height", 256)); + this.c((this.getMaxBuildHeight() + 8) / 16 * 16); + this.c(MathHelper.a(this.getMaxBuildHeight(), 64, 256)); + this.propertyManager.a("max-build-height", Integer.valueOf(this.getMaxBuildHeight())); + i.info("Preparing level \"" + this.O() + "\""); + this.a(this.O(), this.O(), k, worldtype, s2); + long i1 = System.nanoTime() - j; + String s3 = String.format("%.3fs", new Object[] { Double.valueOf((double) i1 / 1.0E9D)}); + + i.info("Done (" + s3 + ")! For help, type \"help\" or \"?\""); + if (this.propertyManager.getBoolean("enable-query", false)) { + i.info("Starting GS4 status listener"); + this.k = new RemoteStatusListener(this); + this.k.a(); + } - if (this.propertyManager.getBoolean("enable-rcon", false)) { - h.info("Starting remote control listener"); - this.k = new RemoteControlListener(this); - this.k.a(); - this.remoteConsole = new org.bukkit.craftbukkit.command.CraftRemoteConsoleCommandSender(); // CraftBukkit - } + if (this.propertyManager.getBoolean("enable-rcon", false)) { + i.info("Starting remote control listener"); + this.l = new RemoteControlListener(this); + this.l.a(); + this.remoteConsole = new org.bukkit.craftbukkit.command.CraftRemoteConsoleCommandSender(); // CraftBukkit + } - // CraftBukkit start - if (this.server.getBukkitSpawnRadius() > -1) { - h.info("'settings.spawn-radius' in bukkit.yml has been moved to 'spawn-protection' in server.properties. I will move your config for you."); - this.propertyManager.properties.remove("spawn-protection"); - this.propertyManager.getInt("spawn-protection", this.server.getBukkitSpawnRadius()); - this.server.removeBukkitSpawnRadius(); - this.propertyManager.savePropertiesFile(); - } + // CraftBukkit start + if (this.server.getBukkitSpawnRadius() > -1) { + i.info("'settings.spawn-radius' in bukkit.yml has been moved to 'spawn-protection' in server.properties. I will move your config for you."); + this.propertyManager.properties.remove("spawn-protection"); + this.propertyManager.getInt("spawn-protection", this.server.getBukkitSpawnRadius()); + this.server.removeBukkitSpawnRadius(); + this.propertyManager.savePropertiesFile(); + } + // CraftBukkit end - return true; + return true; + } } + // CraftBukkit start public PropertyManager getPropertyManager() { return this.propertyManager; } @@ -212,7 +222,7 @@ public class DedicatedServer extends MinecraftServer implements IMinecraftServer } public EnumGamemode getGamemode() { - return this.n; + return this.o; } public EnumDifficulty getDifficulty() { @@ -225,7 +235,7 @@ public class DedicatedServer extends MinecraftServer implements IMinecraftServer protected void a(CrashReport crashreport) { while (this.isRunning()) { - this.ax(); + this.aB(); try { Thread.sleep(10L); @@ -246,9 +256,9 @@ public class DedicatedServer extends MinecraftServer implements IMinecraftServer System.exit(0); } - public void v() { // CraftBukkit - protected -> public + public void v() { // CraftBukkit - protected -> public (decompile error?) super.v(); - this.ax(); + this.aB(); } public boolean getAllowNether() { @@ -260,8 +270,8 @@ public class DedicatedServer extends MinecraftServer implements IMinecraftServer } public void a(MojangStatisticsGenerator mojangstatisticsgenerator) { - mojangstatisticsgenerator.a("whitelist_enabled", Boolean.valueOf(this.ay().getHasWhitelist())); - mojangstatisticsgenerator.a("whitelist_count", Integer.valueOf(this.ay().getWhitelisted().size())); + mojangstatisticsgenerator.a("whitelist_enabled", Boolean.valueOf(this.aC().getHasWhitelist())); + mojangstatisticsgenerator.a("whitelist_count", Integer.valueOf(this.aC().getWhitelisted().length)); super.a(mojangstatisticsgenerator); } @@ -270,12 +280,12 @@ public class DedicatedServer extends MinecraftServer implements IMinecraftServer } public void issueCommand(String s, ICommandListener icommandlistener) { - this.i.add(new ServerCommand(s, icommandlistener)); + this.j.add(new ServerCommand(s, icommandlistener)); } - public void ax() { - while (!this.i.isEmpty()) { - ServerCommand servercommand = (ServerCommand) this.i.remove(0); + public void aB() { + while (!this.j.isEmpty()) { + ServerCommand servercommand = (ServerCommand) this.j.remove(0); // CraftBukkit start - ServerCommand for preprocessing ServerCommandEvent event = new ServerCommandEvent(this.console, servercommand.command); @@ -288,11 +298,11 @@ public class DedicatedServer extends MinecraftServer implements IMinecraftServer } } - public boolean W() { + public boolean X() { return true; } - public DedicatedPlayerList ay() { + public DedicatedPlayerList aC() { return (DedicatedPlayerList) super.getPlayerList(); } @@ -322,13 +332,13 @@ public class DedicatedServer extends MinecraftServer implements IMinecraftServer return file1 != null ? file1.getAbsolutePath() : "No settings file"; } - public void az() { + public void aD() { ServerGUI.a(this); - this.o = true; + this.p = true; } - public boolean aj() { - return this.o; + public boolean ak() { + return this.p; } public String a(EnumGamemode enumgamemode, boolean flag) { @@ -346,9 +356,9 @@ public class DedicatedServer extends MinecraftServer implements IMinecraftServer public boolean a(World world, int i, int j, int k, EntityHuman entityhuman) { if (world.worldProvider.dimension != 0) { return false; - } else if (this.ay().getOPs().isEmpty()) { + } else if (this.aC().getOPs().d()) { return false; - } else if (this.ay().isOp(entityhuman.getName())) { + } else if (this.aC().isOp(entityhuman.getProfile())) { return false; } else if (this.getSpawnProtection() <= 0) { return false; @@ -376,14 +386,89 @@ public class DedicatedServer extends MinecraftServer implements IMinecraftServer return this.propertyManager.getBoolean("broadcast-rcon-to-ops", true); } - public boolean as() { + public boolean at() { return this.propertyManager.getBoolean("announce-player-achievements", true); } + + protected boolean aE() { + boolean flag = false; + + int i; + + for (i = 0; !flag && i <= 2; ++i) { + if (i > 0) { + // CraftBukkit - Fix decompiler stomping on field + DedicatedServer.i.warn("Encountered a problem while converting the user banlist, retrying in a few seconds"); + this.aG(); + } + + flag = NameReferencingFileConverter.a((MinecraftServer) this); + } + + boolean flag1 = false; + + for (i = 0; !flag1 && i <= 2; ++i) { + if (i > 0) { + // CraftBukkit - Fix decompiler stomping on field + DedicatedServer.i.warn("Encountered a problem while converting the ip banlist, retrying in a few seconds"); + this.aG(); + } + + flag1 = NameReferencingFileConverter.b((MinecraftServer) this); + } + + boolean flag2 = false; + + for (i = 0; !flag2 && i <= 2; ++i) { + if (i > 0) { + // CraftBukkit - Fix decompiler stomping on field + DedicatedServer.i.warn("Encountered a problem while converting the op list, retrying in a few seconds"); + this.aG(); + } + + flag2 = NameReferencingFileConverter.c((MinecraftServer) this); + } + + boolean flag3 = false; + + for (i = 0; !flag3 && i <= 2; ++i) { + if (i > 0) { + // CraftBukkit - Fix decompiler stomping on field + DedicatedServer.i.warn("Encountered a problem while converting the whitelist, retrying in a few seconds"); + this.aG(); + } + + flag3 = NameReferencingFileConverter.d((MinecraftServer) this); + } + + boolean flag4 = false; + + for (i = 0; !flag4 && i <= 2; ++i) { + if (i > 0) { + // CraftBukkit - Fix decompiler stomping on field + DedicatedServer.i.warn("Encountered a problem while converting the player save files, retrying in a few seconds"); + this.aG(); + } + + flag4 = NameReferencingFileConverter.a(this, this.propertyManager); + } + + return flag || flag1 || flag2 || flag3 || flag4; + } + + private void aG() { + try { + Thread.sleep(5000L); + } catch (InterruptedException interruptedexception) { + ; + } + } + public PlayerList getPlayerList() { - return this.ay(); + return this.aC(); } - static Logger aA() { - return h; + static Logger aF() { + return i; } } diff --git a/src/main/java/net/minecraft/server/EntityArrow.java b/src/main/java/net/minecraft/server/EntityArrow.java index b263d827..3628774f 100644 --- a/src/main/java/net/minecraft/server/EntityArrow.java +++ b/src/main/java/net/minecraft/server/EntityArrow.java @@ -280,7 +280,7 @@ public class EntityArrow extends Entity implements IProjectile { this.d = movingobjectposition.b; this.e = movingobjectposition.c; this.f = movingobjectposition.d; - this.g = this.world.getType(d, e, f); // CraftBukkit - Get correct block for storage + this.g = this.world.getType(this.d, this.e, this.f); this.h = this.world.getData(this.d, this.e, this.f); this.motX = (double) ((float) (movingobjectposition.pos.a - this.locX)); this.motY = (double) ((float) (movingobjectposition.pos.b - this.locY)); diff --git a/src/main/java/net/minecraft/server/EntityChicken.java b/src/main/java/net/minecraft/server/EntityChicken.java index f65ddccb..9a6daff4 100644 --- a/src/main/java/net/minecraft/server/EntityChicken.java +++ b/src/main/java/net/minecraft/server/EntityChicken.java @@ -59,7 +59,7 @@ public class EntityChicken extends EntityAnimal { } this.bp += this.bt * 2.0F; - if (!this.isBaby() && !this.world.isStatic && --this.bu <= 0) { + if (!this.world.isStatic && !this.isBaby() && !this.bZ() && --this.bu <= 0) { this.makeSound("mob.chicken.plop", 1.0F, (this.random.nextFloat() - this.random.nextFloat()) * 0.2F + 1.0F); this.a(Items.EGG, 1); this.bu = this.random.nextInt(6000) + 6000; diff --git a/src/main/java/net/minecraft/server/EntityHorse.java b/src/main/java/net/minecraft/server/EntityHorse.java index 30f25c3e..5978ea38 100644 --- a/src/main/java/net/minecraft/server/EntityHorse.java +++ b/src/main/java/net/minecraft/server/EntityHorse.java @@ -137,11 +137,11 @@ public class EntityHorse extends EntityAnimal implements IInventoryListener { return this.cb(); } - public String getOwnerName() { + public String getOwnerUUID() { return this.datawatcher.getString(21); } - public void setOwnerName(String s) { + public void setOwnerUUID(String s) { this.datawatcher.watch(21, s); } @@ -875,7 +875,7 @@ public class EntityHorse extends EntityAnimal implements IInventoryListener { } public boolean h(EntityHuman entityhuman) { - this.setOwnerName(entityhuman.getName()); + this.setOwnerUUID(entityhuman.getUniqueID().toString()); this.setTame(true); return true; } @@ -958,7 +958,7 @@ public class EntityHorse extends EntityAnimal implements IInventoryListener { nbttagcompound.setInt("Variant", this.getVariant()); nbttagcompound.setInt("Temper", this.getTemper()); nbttagcompound.setBoolean("Tame", this.isTame()); - nbttagcompound.setString("OwnerName", this.getOwnerName()); + nbttagcompound.setString("OwnerUUID", this.getOwnerUUID()); nbttagcompound.setInt("Bukkit.MaxDomestication", this.maxDomestication); // CraftBukkit if (this.hasChest()) { NBTTagList nbttaglist = new NBTTagList(); @@ -997,8 +997,8 @@ public class EntityHorse extends EntityAnimal implements IInventoryListener { this.setVariant(nbttagcompound.getInt("Variant")); this.setTemper(nbttagcompound.getInt("Temper")); this.setTame(nbttagcompound.getBoolean("Tame")); - if (nbttagcompound.hasKeyOfType("OwnerName", 8)) { - this.setOwnerName(nbttagcompound.getString("OwnerName")); + if (nbttagcompound.hasKeyOfType("OwnerUUID", 8)) { + this.setOwnerUUID(nbttagcompound.getString("OwnerUUID")); } // CraftBukkit start if (nbttagcompound.hasKey("Bukkit.MaxDomestication")) { diff --git a/src/main/java/net/minecraft/server/EntityHuman.java b/src/main/java/net/minecraft/server/EntityHuman.java index 58b7b964..eb4793d9 100644 --- a/src/main/java/net/minecraft/server/EntityHuman.java +++ b/src/main/java/net/minecraft/server/EntityHuman.java @@ -1563,7 +1563,7 @@ public abstract class EntityHuman extends EntityLiving implements ICommandListen } public static UUID a(GameProfile gameprofile) { - UUID uuid = UtilUUID.b(gameprofile.getId()); + UUID uuid = gameprofile.getId(); if (uuid == null) { uuid = UUID.nameUUIDFromBytes(("OfflinePlayer:" + gameprofile.getName()).getBytes(Charsets.UTF_8)); diff --git a/src/main/java/net/minecraft/server/EntityInsentient.java b/src/main/java/net/minecraft/server/EntityInsentient.java index 8c3c8f60..7079ed7d 100644 --- a/src/main/java/net/minecraft/server/EntityInsentient.java +++ b/src/main/java/net/minecraft/server/EntityInsentient.java @@ -804,7 +804,7 @@ public abstract class EntityInsentient extends EntityLiving { return true; } - if (entityhuman.getName().equalsIgnoreCase(((EntityTameableAnimal) this).getOwnerName())) { + if (((EntityTameableAnimal) this).e(entityhuman)) { // CraftBukkit start - fire PlayerLeashEntityEvent if (CraftEventFactory.callPlayerLeashEntityEvent(this, entityhuman, entityhuman).isCancelled()) { ((EntityPlayer) entityhuman).playerConnection.sendPacket(new PacketPlayOutAttachEntity(1, this, this.getLeashHolder())); diff --git a/src/main/java/net/minecraft/server/EntityOcelot.java b/src/main/java/net/minecraft/server/EntityOcelot.java index e75de9c0..7f78fa0a 100644 --- a/src/main/java/net/minecraft/server/EntityOcelot.java +++ b/src/main/java/net/minecraft/server/EntityOcelot.java @@ -114,7 +114,7 @@ public class EntityOcelot extends EntityTameableAnimal { ItemStack itemstack = entityhuman.inventory.getItemInHand(); if (this.isTamed()) { - if (entityhuman.getName().equalsIgnoreCase(this.getOwnerName()) && !this.world.isStatic && !this.c(itemstack)) { + if (this.e(entityhuman) && !this.world.isStatic && !this.c(itemstack)) { this.bp.setSitting(!this.isSitting()); } } else if (this.bq.f() && itemstack != null && itemstack.getItem() == Items.RAW_FISH && entityhuman.f(this) < 9.0D) { @@ -131,7 +131,7 @@ public class EntityOcelot extends EntityTameableAnimal { if (this.random.nextInt(3) == 0 && !org.bukkit.craftbukkit.event.CraftEventFactory.callEntityTameEvent(this, entityhuman).isCancelled()) { this.setTamed(true); this.setCatType(1 + this.world.random.nextInt(3)); - this.setOwnerName(entityhuman.getName()); + this.setOwnerUUID(entityhuman.getUniqueID().toString()); this.i(true); this.bp.setSitting(true); this.world.broadcastEntityEffect(this, (byte) 7); @@ -151,7 +151,7 @@ public class EntityOcelot extends EntityTameableAnimal { EntityOcelot entityocelot = new EntityOcelot(this.world); if (this.isTamed()) { - entityocelot.setOwnerName(this.getOwnerName()); + entityocelot.setOwnerUUID(this.getOwnerUUID()); entityocelot.setTamed(true); entityocelot.setCatType(this.getCatType()); } diff --git a/src/main/java/net/minecraft/server/EntityPlayer.java b/src/main/java/net/minecraft/server/EntityPlayer.java index 8d98a706..9b80aef5 100644 --- a/src/main/java/net/minecraft/server/EntityPlayer.java +++ b/src/main/java/net/minecraft/server/EntityPlayer.java @@ -82,7 +82,7 @@ public class EntityPlayer extends EntityHuman implements ICrafting { } this.server = minecraftserver; - this.bO = minecraftserver.getPlayerList().i(this.getName()); + this.bO = minecraftserver.getPlayerList().a((EntityHuman) this); this.W = 0.0F; this.height = 0.0F; this.setPositionRotation((double) i + 0.5D, (double) k, (double) j + 0.5D, 0.0F, 0.0F); @@ -235,7 +235,7 @@ public class EntityPlayer extends EntityHuman implements ICrafting { } } - if (this.bX > 0L && this.server.getIdleTimeout() > 0 && MinecraftServer.aq() - this.bX > (long) (this.server.getIdleTimeout() * 1000 * 60)) { + if (this.bX > 0L && this.server.getIdleTimeout() > 0 && MinecraftServer.ar() - this.bX > (long) (this.server.getIdleTimeout() * 1000 * 60)) { this.playerConnection.disconnect("You have been idle for too long!"); } } @@ -428,7 +428,7 @@ public class EntityPlayer extends EntityHuman implements ICrafting { return false; } else { // CraftBukkit - this.server.getPvP() -> this.world.pvpMode - boolean flag = this.server.W() && this.world.pvpMode && "fall".equals(damagesource.translationIndex); + boolean flag = this.server.X() && this.world.pvpMode && "fall".equals(damagesource.translationIndex); if (!flag && this.invulnerableTicks > 0 && damagesource != DamageSource.OUT_OF_WORLD) { return false; @@ -923,7 +923,19 @@ public class EntityPlayer extends EntityHuman implements ICrafting { } public boolean a(int i, String s) { - return "seed".equals(s) && !this.server.W() ? true : (!"tell".equals(s) && !"help".equals(s) && !"me".equals(s) ? (this.server.getPlayerList().isOp(this.getName()) ? this.server.l() >= i : false) : true); + if ("seed".equals(s) && !this.server.X()) { + return true; + } else if (!"tell".equals(s) && !"help".equals(s) && !"me".equals(s)) { + if (this.server.getPlayerList().isOp(this.getProfile())) { + OpListEntry oplistentry = (OpListEntry) this.server.getPlayerList().getOPs().get(this.getProfile()); + + return oplistentry != null ? oplistentry.a() >= i : this.server.l() >= i; + } else { + return false; + } + } else { + return true; + } } public String s() { @@ -944,7 +956,7 @@ public class EntityPlayer extends EntityHuman implements ICrafting { this.bV = packetplayinsettings.e(); this.bW = packetplayinsettings.f(); - if (this.server.M() && this.server.L().equals(this.getName())) { + if (this.server.N() && this.server.M().equals(this.getName())) { this.server.a(packetplayinsettings.g()); } @@ -964,7 +976,7 @@ public class EntityPlayer extends EntityHuman implements ICrafting { } public void v() { - this.bX = MinecraftServer.aq(); + this.bX = MinecraftServer.ar(); } public ServerStatisticManager getStatisticManager() { diff --git a/src/main/java/net/minecraft/server/EntityTracker.java b/src/main/java/net/minecraft/server/EntityTracker.java index af440b9c..1af0e67e 100644 --- a/src/main/java/net/minecraft/server/EntityTracker.java +++ b/src/main/java/net/minecraft/server/EntityTracker.java @@ -19,7 +19,7 @@ public class EntityTracker { public EntityTracker(WorldServer worldserver) { this.world = worldserver; - this.e = worldserver.getMinecraftServer().getPlayerList().a(); + this.e = worldserver.getMinecraftServer().getPlayerList().d(); } public void track(Entity entity) { diff --git a/src/main/java/net/minecraft/server/EntityWolf.java b/src/main/java/net/minecraft/server/EntityWolf.java index 097f4f56..dc144413 100644 --- a/src/main/java/net/minecraft/server/EntityWolf.java +++ b/src/main/java/net/minecraft/server/EntityWolf.java @@ -231,7 +231,7 @@ public class EntityWolf extends EntityTameableAnimal { } } - if (entityhuman.getName().equalsIgnoreCase(this.getOwnerName()) && !this.world.isStatic && !this.c(itemstack)) { + if (this.e(entityhuman) && !this.world.isStatic && !this.c(itemstack)) { this.bp.setSitting(!this.isSitting()); this.bc = false; this.setPathEntity((PathEntity) null); @@ -255,7 +255,7 @@ public class EntityWolf extends EntityTameableAnimal { this.setGoalTarget((EntityLiving) null); this.bp.setSitting(true); this.setHealth(this.getMaxHealth()); // CraftBukkit - 20.0 -> getMaxHealth() - this.setOwnerName(entityhuman.getName()); + this.setOwnerUUID(entityhuman.getUniqueID().toString()); this.i(true); this.world.broadcastEntityEffect(this, (byte) 7); } else { @@ -302,10 +302,10 @@ public class EntityWolf extends EntityTameableAnimal { public EntityWolf b(EntityAgeable entityageable) { EntityWolf entitywolf = new EntityWolf(this.world); - String s = this.getOwnerName(); + String s = this.getOwnerUUID(); if (s != null && s.trim().length() > 0) { - entitywolf.setOwnerName(s); + entitywolf.setOwnerUUID(s); entitywolf.setTamed(true); } diff --git a/src/main/java/net/minecraft/server/EntityZombie.java b/src/main/java/net/minecraft/server/EntityZombie.java index b751d01c..a0b6f62e 100644 --- a/src/main/java/net/minecraft/server/EntityZombie.java +++ b/src/main/java/net/minecraft/server/EntityZombie.java @@ -327,7 +327,7 @@ public class EntityZombie extends EntityMonster { public void a(EntityLiving entityliving) { super.a(entityliving); if ((this.world.difficulty == EnumDifficulty.NORMAL || this.world.difficulty == EnumDifficulty.HARD) && entityliving instanceof EntityVillager) { - if (this.random.nextBoolean()) { + if (this.world.difficulty != EnumDifficulty.HARD && this.random.nextBoolean()) { return; } diff --git a/src/main/java/net/minecraft/server/ExpirableListEntry.java b/src/main/java/net/minecraft/server/ExpirableListEntry.java new file mode 100644 index 00000000..7b41cab8 --- /dev/null +++ b/src/main/java/net/minecraft/server/ExpirableListEntry.java @@ -0,0 +1,79 @@ +package net.minecraft.server; + +import java.text.ParseException; +import java.text.SimpleDateFormat; +import java.util.Date; + +import net.minecraft.util.com.google.gson.JsonObject; + +public abstract class ExpirableListEntry extends JsonListEntry { + + public static final SimpleDateFormat a = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss Z"); + protected final Date b; + protected final String c; + protected final Date d; + protected final String e; + + public ExpirableListEntry(Object object, Date date, String s, Date date1, String s1) { + super(object); + this.b = date == null ? new Date() : date; + this.c = s == null ? "(Unknown)" : s; + this.d = date1; + this.e = s1 == null ? "Banned by an operator." : s1; + } + + protected ExpirableListEntry(Object object, JsonObject jsonobject) { + super(object, jsonobject); + + Date date; + + try { + date = jsonobject.has("created") ? a.parse(jsonobject.get("created").getAsString()) : new Date(); + } catch (ParseException parseexception) { + date = new Date(); + } + + this.b = date; + this.c = jsonobject.has("source") ? jsonobject.get("source").getAsString() : "(Unknown)"; + + Date date1; + + try { + date1 = jsonobject.has("expires") ? a.parse(jsonobject.get("expires").getAsString()) : null; + } catch (ParseException parseexception1) { + date1 = null; + } + + this.d = date1; + this.e = jsonobject.has("reason") ? jsonobject.get("reason").getAsString() : "Banned by an operator."; + } + + public Date getExpires() { + return this.d; + } + + public String getReason() { + return this.e; + } + + boolean e() { + return this.d == null ? false : this.d.before(new Date()); + } + + protected void a(JsonObject jsonobject) { + jsonobject.addProperty("created", a.format(this.b)); + jsonobject.addProperty("source", this.c); + jsonobject.addProperty("expires", this.d == null ? "forever" : a.format(this.d)); + jsonobject.addProperty("reason", this.e); + } + + // CraftBukkit start + public String getSource() { + return this.c; + } + + public Date getCreated() { + return this.b; + } + // CraftBukkit end +} diff --git a/src/main/java/net/minecraft/server/FileConversionException.java b/src/main/java/net/minecraft/server/FileConversionException.java new file mode 100644 index 00000000..4b189bfb --- /dev/null +++ b/src/main/java/net/minecraft/server/FileConversionException.java @@ -0,0 +1,22 @@ +package net.minecraft.server; + +// CraftBukkit - Imported because it's package private + +class FileConversionException extends RuntimeException { + + private FileConversionException(String s, Throwable throwable) { + super(s, throwable); + } + + private FileConversionException(String s) { + super(s); + } + + FileConversionException(String s, PredicateEmptyList predicateemptylist) { + this(s); + } + + FileConversionException(String s, Throwable throwable, PredicateEmptyList predicateemptylist) { + this(s, throwable); + } +} diff --git a/src/main/java/net/minecraft/server/HandshakeListener.java b/src/main/java/net/minecraft/server/HandshakeListener.java index e5992f85..17e69dbc 100644 --- a/src/main/java/net/minecraft/server/HandshakeListener.java +++ b/src/main/java/net/minecraft/server/HandshakeListener.java @@ -63,12 +63,12 @@ public class HandshakeListener implements PacketHandshakingInListener { } // CraftBukkit end - if (packethandshakinginsetprotocol.d() > 4) { - chatcomponenttext = new ChatComponentText("Outdated server! I\'m still on 1.7.5"); + if (packethandshakinginsetprotocol.d() > 5) { + chatcomponenttext = new ChatComponentText("Outdated server! I\'m still on 1.7.8"); this.b.handle(new PacketLoginOutDisconnect(chatcomponenttext), new GenericFutureListener[0]); this.b.close(chatcomponenttext); - } else if (packethandshakinginsetprotocol.d() < 4) { - chatcomponenttext = new ChatComponentText("Outdated client! Please use 1.7.5"); + } else if (packethandshakinginsetprotocol.d() < 5) { + chatcomponenttext = new ChatComponentText("Outdated client! Please use 1.7.8"); this.b.handle(new PacketLoginOutDisconnect(chatcomponenttext), new GenericFutureListener[0]); this.b.close(chatcomponenttext); } else { diff --git a/src/main/java/net/minecraft/server/ItemSkull.java b/src/main/java/net/minecraft/server/ItemSkull.java index 6b2bf9bb..dd7e5ccf 100644 --- a/src/main/java/net/minecraft/server/ItemSkull.java +++ b/src/main/java/net/minecraft/server/ItemSkull.java @@ -1,5 +1,9 @@ package net.minecraft.server; +import java.util.UUID; + +import net.minecraft.util.com.mojang.authlib.GameProfile; + public class ItemSkull extends Item { private static final String[] b = new String[] { "skeleton", "wither", "zombie", "char", "creeper"}; @@ -38,11 +42,7 @@ public class ItemSkull extends Item { ++i; } - if (!entityhuman.a(i, j, k, l, itemstack)) { - return false; - } else if (!Blocks.SKULL.canPlace(world, i, j, k)) { - return false; - } else { + if (!world.isStatic) { // CraftBukkit start - Handle in ItemBlock // world.setTypeAndData(i, j, k, Blocks.SKULL, l, 2); if (!ItemBlock.processBlockPlace(world, entityhuman, null, i, j, k, Blocks.SKULL, l, clickedX, clickedY, clickedZ)) { @@ -59,20 +59,32 @@ public class ItemSkull extends Item { TileEntity tileentity = world.getTileEntity(i, j, k); if (tileentity != null && tileentity instanceof TileEntitySkull) { - String s = ""; - - if (itemstack.hasTag() && itemstack.getTag().hasKeyOfType("SkullOwner", 8)) { - s = itemstack.getTag().getString("SkullOwner"); + if (itemstack.getData() == 3) { + GameProfile gameprofile = null; + + if (itemstack.hasTag()) { + NBTTagCompound nbttagcompound = itemstack.getTag(); + + if (nbttagcompound.hasKeyOfType("SkullOwner", 10)) { + gameprofile = GameProfileSerializer.a(nbttagcompound.getCompound("SkullOwner")); + } else if (nbttagcompound.hasKeyOfType("SkullOwner", 8) && nbttagcompound.getString("SkullOwner").length() > 0) { + gameprofile = new GameProfile((UUID) null, nbttagcompound.getString("SkullOwner")); + } + } + + ((TileEntitySkull) tileentity).setGameProfile(gameprofile); + } else { + ((TileEntitySkull) tileentity).setSkullType(itemstack.getData()); } - ((TileEntitySkull) tileentity).setSkullType(itemstack.getData(), s); ((TileEntitySkull) tileentity).setRotation(i1); ((BlockSkull) Blocks.SKULL).a(world, i, j, k, (TileEntitySkull) tileentity); } --itemstack.count; - return true; } + + return true; } } @@ -91,6 +103,16 @@ public class ItemSkull extends Item { } public String n(ItemStack itemstack) { - return itemstack.getData() == 3 && itemstack.hasTag() && itemstack.getTag().hasKeyOfType("SkullOwner", 8) ? LocaleI18n.get("item.skull.player.name", new Object[] { itemstack.getTag().getString("SkullOwner")}) : super.n(itemstack); + if (itemstack.getData() == 3 && itemstack.hasTag()) { + if (itemstack.getTag().hasKeyOfType("SkullOwner", 10)) { + return LocaleI18n.get("item.skull.player.name", new Object[] { GameProfileSerializer.a(itemstack.getTag().getCompound("SkullOwner")).getName()}); + } + + if (itemstack.getTag().hasKeyOfType("SkullOwner", 8)) { + return LocaleI18n.get("item.skull.player.name", new Object[] { itemstack.getTag().getString("SkullOwner")}); + } + } + + return super.n(itemstack); } } diff --git a/src/main/java/net/minecraft/server/LoginListener.java b/src/main/java/net/minecraft/server/LoginListener.java index dddd9aa3..8f982f17 100644 --- a/src/main/java/net/minecraft/server/LoginListener.java +++ b/src/main/java/net/minecraft/server/LoginListener.java @@ -61,9 +61,7 @@ public class LoginListener implements PacketLoginInListener { public void c() { if (!this.i.isComplete()) { - UUID uuid = UUID.nameUUIDFromBytes(("OfflinePlayer:" + this.i.getName()).getBytes(Charsets.UTF_8)); - - this.i = new GameProfile(uuid.toString().replaceAll("-", ""), this.i.getName()); + this.i = this.a(this.i); } // CraftBukkit start - fire PlayerLoginEvent @@ -97,7 +95,7 @@ public class LoginListener implements PacketLoginInListener { this.i = packetlogininstart.c(); if (this.server.getOnlineMode() && !this.networkManager.c()) { this.g = EnumProtocolState.KEY; - this.networkManager.handle(new PacketLoginOutEncryptionBegin(this.j, this.server.J().getPublic(), this.e), new GenericFutureListener[0]); + this.networkManager.handle(new PacketLoginOutEncryptionBegin(this.j, this.server.K().getPublic(), this.e), new GenericFutureListener[0]); } else { this.g = EnumProtocolState.READY_TO_ACCEPT; } @@ -105,7 +103,7 @@ public class LoginListener implements PacketLoginInListener { public void a(PacketLoginInEncryptionBegin packetlogininencryptionbegin) { Validate.validState(this.g == EnumProtocolState.KEY, "Unexpected key packet", new Object[0]); - PrivateKey privatekey = this.server.J().getPrivate(); + PrivateKey privatekey = this.server.K().getPrivate(); if (!Arrays.equals(this.e, packetlogininencryptionbegin.b(privatekey))) { throw new IllegalStateException("Invalid nonce!"); @@ -117,15 +115,25 @@ public class LoginListener implements PacketLoginInListener { } } - static String a(LoginListener loginlistener) { + protected GameProfile a(GameProfile gameprofile) { + UUID uuid = UUID.nameUUIDFromBytes(("OfflinePlayer:" + gameprofile.getName()).getBytes(Charsets.UTF_8)); + + return new GameProfile(uuid, gameprofile.getName()); + } + + static GameProfile a(LoginListener loginlistener) { + return loginlistener.i; + } + + static String b(LoginListener loginlistener) { return loginlistener.j; } - static MinecraftServer b(LoginListener loginlistener) { + static MinecraftServer c(LoginListener loginlistener) { return loginlistener.server; } - static SecretKey c(LoginListener loginlistener) { + static SecretKey d(LoginListener loginlistener) { return loginlistener.loginKey; } @@ -133,10 +141,6 @@ public class LoginListener implements PacketLoginInListener { return loginlistener.i = gameprofile; } - static GameProfile d(LoginListener loginlistener) { - return loginlistener.i; - } - static Logger e() { return c; } diff --git a/src/main/java/net/minecraft/server/MinecraftServer.java b/src/main/java/net/minecraft/server/MinecraftServer.java index 6788c5d3..00bb455a 100644 --- a/src/main/java/net/minecraft/server/MinecraftServer.java +++ b/src/main/java/net/minecraft/server/MinecraftServer.java @@ -19,6 +19,7 @@ import javax.imageio.ImageIO; import net.minecraft.util.com.google.common.base.Charsets; import net.minecraft.util.com.mojang.authlib.GameProfile; +import net.minecraft.util.com.mojang.authlib.GameProfileRepository; import net.minecraft.util.com.mojang.authlib.minecraft.MinecraftSessionService; import net.minecraft.util.com.mojang.authlib.yggdrasil.YggdrasilAuthenticationService; import net.minecraft.util.io.netty.buffer.ByteBuf; @@ -43,51 +44,55 @@ import org.bukkit.event.world.WorldSaveEvent; public abstract class MinecraftServer implements ICommandListener, Runnable, IMojangStatistics { - private static final Logger h = LogManager.getLogger(); - private static MinecraftServer i; + private static final Logger i = LogManager.getLogger(); + private static final File a = new File("usercache.json"); + private static MinecraftServer j; public Convertable convertable; // CraftBukkit - private final -> public - private final MojangStatisticsGenerator k = new MojangStatisticsGenerator("server", this, aq()); + private final MojangStatisticsGenerator l = new MojangStatisticsGenerator("server", this, ar()); public File universe; // CraftBukkit - private final -> public - private final List m = new ArrayList(); - private final ICommandHandler n; + private final List n = new ArrayList(); + private final ICommandHandler o; public final MethodProfiler methodProfiler = new MethodProfiler(); - private final ServerConnection o; - private final ServerPing p = new ServerPing(); - private final Random q = new Random(); + private final ServerConnection p; + private final ServerPing q = new ServerPing(); + private final Random r = new Random(); private String serverIp; - private int s = -1; + private int t = -1; public WorldServer[] worldServer; - private PlayerList t; + private PlayerList u; private boolean isRunning = true; private boolean isStopped; private int ticks; - protected final Proxy c; - public String d; - public int e; + protected final Proxy d; + public String e; + public int f; private boolean onlineMode; private boolean spawnAnimals; private boolean spawnNPCs; private boolean pvpMode; private boolean allowFlight; private String motd; - private int D; - private int E = 0; - public final long[] f = new long[100]; - public long[][] g; - private KeyPair F; - private String G; + private int E; + private int F = 0; + public final long[] g = new long[100]; + public long[][] h; + private KeyPair G; private String H; + private String I; private boolean demoMode; - private boolean K; private boolean L; - private String M = ""; - private boolean N; - private long O; - private String P; - private boolean Q; + private boolean M; + private String N = ""; + private boolean O; + private long P; + private String Q; private boolean R; - private final MinecraftSessionService S; - private long T = 0L; + private boolean S; + private final YggdrasilAuthenticationService T; + private final MinecraftSessionService U; + private long V = 0L; + private final GameProfileRepository W; + private final UserCache X; // CraftBukkit start - add fields public List<WorldServer> worlds = new ArrayList<WorldServer>(); @@ -103,14 +108,16 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo // CraftBukkit end public MinecraftServer(OptionSet options, Proxy proxy) { // CraftBukkit - signature file -> OptionSet - i = this; - this.c = proxy; + this.X = new UserCache(this, a); + j = this; + this.d = proxy; // this.universe = file1; // CraftBukkit - this.o = new ServerConnection(this); - this.n = new CommandDispatcher(); + this.p = new ServerConnection(this); + this.o = new CommandDispatcher(); // this.convertable = new WorldLoaderServer(file1); // CraftBukkit - moved to DedicatedServer.init - this.S = (new YggdrasilAuthenticationService(proxy, UUID.randomUUID().toString())).createMinecraftSessionService(); - + this.T = new YggdrasilAuthenticationService(proxy, UUID.randomUUID().toString()); + this.U = this.T.createMinecraftSessionService(); + this.W = this.T.createProfileRepository(); // CraftBukkit start this.options = options; // Try to see if we're actually running in a terminal, disable jline if not @@ -131,7 +138,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo this.reader = new ConsoleReader(System.in, System.out); this.reader.setExpandEvents(false); } catch (IOException ex) { - h.warn((String) null, ex); + i.warn((String) null, ex); } } Runtime.getRuntime().addShutdownHook(new org.bukkit.craftbukkit.util.ServerShutdownThread(this)); @@ -146,21 +153,21 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo protected void a(String s) { if (this.getConvertable().isConvertable(s)) { - h.info("Converting map!"); + i.info("Converting map!"); this.b("menu.convertingLevel"); this.getConvertable().convert(s, new ConvertProgressUpdater(this)); } } protected synchronized void b(String s) { - this.P = s; + this.Q = s; } protected void a(String s, String s1, long i, WorldType worldtype, String s2) { this.a(s); this.b("menu.loadingLevel"); this.worldServer = new WorldServer[3]; - // this.g = new long[this.worldServer.length][100]; // CraftBukkit - Removed ticktime arrays + // this.h = new long[this.worldServer.length][100]; // CraftBukkit - Removed ticktime arrays // IDataManager idatamanager = this.convertable.a(s, true); // WorldData worlddata = idatamanager.getWorldData(); /* CraftBukkit start - Removed worldsettings @@ -173,7 +180,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo worldsettings = new WorldSettings(worlddata); } - if (this.K) { + if (this.L) { worldsettings.a(); } // */ @@ -208,7 +215,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo if (j == 0) { IDataManager idatamanager = new ServerNBTManager(server.getWorldContainer(), s1, true); - if (this.Q()) { + if (this.R()) { world = new DemoWorldServer(this, idatamanager, s1, dimension, this.methodProfiler); } else { // world =, b0 to dimension, added Environment and gen @@ -222,31 +229,31 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo File oldWorld = new File(new File(s), dim); if ((!newWorld.isDirectory()) && (oldWorld.isDirectory())) { - h.info("---- Migration of old " + worldType + " folder required ----"); - h.info("Unfortunately due to the way that Minecraft implemented multiworld support in 1.6, Bukkit requires that you move your " + worldType + " folder to a new location in order to operate correctly."); - h.info("We will move this folder for you, but it will mean that you need to move it back should you wish to stop using Bukkit in the future."); - h.info("Attempting to move " + oldWorld + " to " + newWorld + "..."); + MinecraftServer.i.info("---- Migration of old " + worldType + " folder required ----"); + MinecraftServer.i.info("Unfortunately due to the way that Minecraft implemented multiworld support in 1.6, Bukkit requires that you move your " + worldType + " folder to a new location in order to operate correctly."); + MinecraftServer.i.info("We will move this folder for you, but it will mean that you need to move it back should you wish to stop using Bukkit in the future."); + MinecraftServer.i.info("Attempting to move " + oldWorld + " to " + newWorld + "..."); if (newWorld.exists()) { - h.warn("A file or folder already exists at " + newWorld + "!"); - h.info("---- Migration of old " + worldType + " folder failed ----"); + MinecraftServer.i.warn("A file or folder already exists at " + newWorld + "!"); + MinecraftServer.i.info("---- Migration of old " + worldType + " folder failed ----"); } else if (newWorld.getParentFile().mkdirs()) { if (oldWorld.renameTo(newWorld)) { - h.info("Success! To restore " + worldType + " in the future, simply move " + newWorld + " to " + oldWorld); + MinecraftServer.i.info("Success! To restore " + worldType + " in the future, simply move " + newWorld + " to " + oldWorld); // Migrate world data too. try { com.google.common.io.Files.copy(new File(new File(s), "level.dat"), new File(new File(name), "level.dat")); } catch (IOException exception) { - h.warn("Unable to migrate world data."); + MinecraftServer.i.warn("Unable to migrate world data."); } - h.info("---- Migration of old " + worldType + " folder complete ----"); + MinecraftServer.i.info("---- Migration of old " + worldType + " folder complete ----"); } else { - h.warn("Could not move folder " + oldWorld + " to " + newWorld + "!"); - h.info("---- Migration of old " + worldType + " folder failed ----"); + MinecraftServer.i.warn("Could not move folder " + oldWorld + " to " + newWorld + "!"); + MinecraftServer.i.info("---- Migration of old " + worldType + " folder failed ----"); } } else { - h.warn("Could not create path for " + newWorld + "!"); - h.info("---- Migration of old " + worldType + " folder failed ----"); + MinecraftServer.i.warn("Could not create path for " + newWorld + "!"); + MinecraftServer.i.info("---- Migration of old " + worldType + " folder failed ----"); } } @@ -262,12 +269,12 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo this.server.getPluginManager().callEvent(new org.bukkit.event.world.WorldInitEvent(world.getWorld())); world.addIWorldAccess(new WorldManager(this, world)); - if (!this.M()) { + if (!this.N()) { world.getWorldData().setGameType(this.getGamemode()); } this.worlds.add(world); - this.t.setPlayerFileData(this.worlds.toArray(new WorldServer[this.worlds.size()])); + this.u.setPlayerFileData(this.worlds.toArray(new WorldServer[this.worlds.size()])); // CraftBukkit end } @@ -288,18 +295,18 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo // CraftBukkit start - fire WorldLoadEvent and handle whether or not to keep the spawn in memory for (int m = 0; m < this.worlds.size(); ++m) { WorldServer worldserver = this.worlds.get(m); - h.info("Preparing start region for level " + m + " (Seed: " + worldserver.getSeed() + ")"); + MinecraftServer.i.info("Preparing start region for level " + m + " (Seed: " + worldserver.getSeed() + ")"); if (!worldserver.getWorld().getKeepSpawnInMemory()) { continue; } ChunkCoordinates chunkcoordinates = worldserver.getSpawn(); - long j = aq(); + long j = ar(); i = 0; for (int k = -192; k <= 192 && this.isRunning(); k += 16) { for (int l = -192; l <= 192 && this.isRunning(); l += 16) { - long i1 = aq(); + long i1 = ar(); if (i1 - j > 1000L) { this.a_("Preparing spawn area", i * 100 / 625); @@ -332,20 +339,21 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo public abstract boolean m(); protected void a_(String s, int i) { - this.d = s; - this.e = i; - h.info(s + ": " + i + "%"); + this.e = s; + this.f = i; + // CraftBukkit - Use FQN to work around decompiler issue + MinecraftServer.i.info(s + ": " + i + "%"); } protected void n() { - this.d = null; - this.e = 0; + this.e = null; + this.f = 0; this.server.enablePlugins(org.bukkit.plugin.PluginLoadOrder.POSTWORLD); // CraftBukkit } protected void saveChunks(boolean flag) throws ExceptionWorldConflict { // CraftBukkit - added throws - if (!this.L) { + if (!this.M) { // CraftBukkit start - fire WorldSaveEvent // WorldServer[] aworldserver = this.worldServer; int i = this.worlds.size(); @@ -355,7 +363,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo if (worldserver != null) { if (!flag) { - h.info("Saving chunks for level \'" + worldserver.getWorldData().getName() + "\'/" + worldserver.worldProvider.getName()); + MinecraftServer.i.info("Saving chunks for level \'" + worldserver.getWorldData().getName() + "\'/" + worldserver.worldProvider.getName()); } worldserver.save(true, (IProgressUpdate) null); @@ -370,37 +378,39 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } public void stop() throws ExceptionWorldConflict { // CraftBukkit - added throws - if (!this.L) { - h.info("Stopping server"); + if (!this.M) { + i.info("Stopping server"); // CraftBukkit start if (this.server != null) { this.server.disablePlugins(); } // CraftBukkit end - if (this.ah() != null) { - this.ah().b(); + if (this.ai() != null) { + this.ai().b(); } - if (this.t != null) { - h.info("Saving players"); - this.t.savePlayers(); - this.t.r(); + if (this.u != null) { + i.info("Saving players"); + this.u.savePlayers(); + this.u.u(); } - h.info("Saving worlds"); - this.saveChunks(false); - - /* CraftBukkit start - Handled in saveChunks - for (int i = 0; i < this.worldServer.length; ++i) { - WorldServer worldserver = this.worldServer[i]; + if (this.worldServer != null) { + i.info("Saving worlds"); + this.saveChunks(false); + + /* CraftBukkit start - Handled in saveChunks + for (int i = 0; i < this.worldServer.length; ++i) { + WorldServer worldserver = this.worldServer[i]; - worldserver.saveLevel(); + worldserver.saveLevel(); + } + // CraftBukkit end */ } - // CraftBukkit end */ - if (this.k.d()) { - this.k.e(); + if (this.l.d()) { + this.l.e(); } } } @@ -424,26 +434,26 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo public void run() { try { if (this.init()) { - long i = aq(); + long i = ar(); long j = 0L; - this.p.setMOTD(new ChatComponentText(this.motd)); - this.p.setServerInfo(new ServerPingServerData("1.7.5", 4)); - this.a(this.p); + this.q.setMOTD(new ChatComponentText(this.motd)); + this.q.setServerInfo(new ServerPingServerData("1.7.8", 5)); + this.a(this.q); while (this.isRunning) { - long k = aq(); + long k = ar(); long l = k - i; - if (l > 2000L && i - this.O >= 15000L) { + if (l > 2000L && i - this.P >= 15000L) { if (this.server.getWarnOnOverload()) // CraftBukkit - Added option to suppress warning messages - h.warn("Can\'t keep up! Did the system time change, or is the server overloaded? Running {}ms behind, skipping {} tick(s)", new Object[] { Long.valueOf(l), Long.valueOf(l / 50L)}); + MinecraftServer.i.warn("Can\'t keep up! Did the system time change, or is the server overloaded? Running {}ms behind, skipping {} tick(s)", new Object[] { Long.valueOf(l), Long.valueOf(l / 50L)}); l = 2000L; - this.O = i; + this.P = i; } if (l < 0L) { - h.warn("Time ran backwards! Did the system time change?"); + MinecraftServer.i.warn("Time ran backwards! Did the system time change?"); l = 0L; } @@ -461,13 +471,13 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } Thread.sleep(Math.max(1L, 50L - j)); - this.N = true; + this.O = true; } } else { this.a((CrashReport) null); } } catch (Throwable throwable) { - h.error("Encountered an unexpected exception", throwable); + i.error("Encountered an unexpected exception", throwable); CrashReport crashreport = null; if (throwable instanceof ReportedException) { @@ -479,9 +489,9 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo File file1 = new File(new File(this.s(), "crash-reports"), "crash-" + (new SimpleDateFormat("yyyy-MM-dd_HH.mm.ss")).format(new Date()) + "-server.txt"); if (crashreport.a(file1)) { - h.error("This crash report has been saved to: " + file1.getAbsolutePath()); + i.error("This crash report has been saved to: " + file1.getAbsolutePath()); } else { - h.error("We were unable to save this crash report to disk."); + i.error("We were unable to save this crash report to disk."); } this.a(crashreport); @@ -490,7 +500,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo this.stop(); this.isStopped = true; } catch (Throwable throwable1) { - h.error("Exception stopping the server", throwable1); + i.error("Exception stopping the server", throwable1); } finally { // CraftBukkit start - Restore terminal to original settings try { @@ -519,7 +529,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo serverping.setFavicon("data:image/png;base64," + bytebuf1.toString(Charsets.UTF_8)); } catch (Exception exception) { - h.error("Couldn\'t load server icon", exception); + i.error("Couldn\'t load server icon", exception); } finally { bytebuf.release(); } @@ -538,45 +548,45 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo long i = System.nanoTime(); ++this.ticks; - if (this.Q) { - this.Q = false; + if (this.R) { + this.R = false; this.methodProfiler.a = true; this.methodProfiler.a(); } this.methodProfiler.a("root"); this.v(); - if (i - this.T >= 5000000000L) { - this.T = i; - this.p.setPlayerSample(new ServerPingPlayerSample(this.D(), this.C())); + if (i - this.V >= 5000000000L) { + this.V = i; + this.q.setPlayerSample(new ServerPingPlayerSample(this.D(), this.C())); GameProfile[] agameprofile = new GameProfile[Math.min(this.C(), 12)]; - int j = MathHelper.nextInt(this.q, 0, this.C() - agameprofile.length); + int j = MathHelper.nextInt(this.r, 0, this.C() - agameprofile.length); for (int k = 0; k < agameprofile.length; ++k) { - agameprofile[k] = ((EntityPlayer) this.t.players.get(j + k)).getProfile(); + agameprofile[k] = ((EntityPlayer) this.u.players.get(j + k)).getProfile(); } Collections.shuffle(Arrays.asList(agameprofile)); - this.p.b().a(agameprofile); + this.q.b().a(agameprofile); } if ((this.autosavePeriod > 0) && ((this.ticks % this.autosavePeriod) == 0)) { // CraftBukkit this.methodProfiler.a("save"); - this.t.savePlayers(); + this.u.savePlayers(); this.saveChunks(true); this.methodProfiler.b(); } this.methodProfiler.a("tallying"); - this.f[this.ticks % 100] = System.nanoTime() - i; + this.g[this.ticks % 100] = System.nanoTime() - i; this.methodProfiler.b(); this.methodProfiler.a("snooper"); - if (!this.k.d() && this.ticks > 100) { - this.k.a(); + if (!this.l.d() && this.ticks > 100) { + this.l.a(); } if (this.ticks % 6000 == 0) { - this.k.b(); + this.l.b(); } this.methodProfiler.b(); @@ -650,17 +660,17 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo this.methodProfiler.b(); // } // CraftBukkit - // this.g[i][this.ticks % 100] = System.nanoTime() - j; // CraftBukkit + // this.h[i][this.ticks % 100] = System.nanoTime() - j; // CraftBukkit } this.methodProfiler.c("connection"); - this.ah().c(); + this.ai().c(); this.methodProfiler.c("players"); - this.t.tick(); + this.u.tick(); this.methodProfiler.c("tickables"); - for (i = 0; i < this.m.size(); ++i) { - ((IUpdatePlayerListBox) this.m.get(i)).a(); + for (i = 0; i < this.n.size(); ++i) { + ((IUpdatePlayerListBox) this.n.get(i)).a(); } this.methodProfiler.b(); @@ -671,7 +681,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } public void a(IUpdatePlayerListBox iupdateplayerlistbox) { - this.m.add(iupdateplayerlistbox); + this.n.add(iupdateplayerlistbox); } public static void main(final OptionSet options) { // CraftBukkit - replaces main(String[] astring) @@ -747,7 +757,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } if (flag) { - dedicatedserver.az(); + dedicatedserver.aD(); } // */ @@ -772,7 +782,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo // Runtime.getRuntime().addShutdownHook(new ThreadShutdown("Server Shutdown Thread", dedicatedserver)); // CraftBukkit end } catch (Exception exception) { - h.fatal("Failed to start the minecraft server", exception); + i.fatal("Failed to start the minecraft server", exception); } } @@ -785,11 +795,11 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } public void info(String s) { - h.info(s); + i.info(s); } public void warning(String s) { - h.warn(s); + i.warn(s); } public WorldServer getWorldServer(int i) { @@ -809,7 +819,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } public int z() { - return this.s; + return this.t; } public String A() { @@ -817,19 +827,23 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } public String getVersion() { - return "1.7.5"; + return "1.7.8"; } public int C() { - return this.t.getPlayerCount(); + return this.u.getPlayerCount(); } public int D() { - return this.t.getMaxPlayers(); + return this.u.getMaxPlayers(); } public String[] getPlayers() { - return this.t.d(); + return this.u.f(); + } + + public GameProfile[] F() { + return this.u.g(); } public String getPlugins() { @@ -871,7 +885,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo // Event changes end ServerCommand servercommand = new ServerCommand(event.getCommand(), RemoteControlCommandListener.instance); MinecraftServer.this.server.dispatchServerCommand(MinecraftServer.this.remoteConsole, servercommand); // CraftBukkit - // this.n.a(RemoteControlCommandListener.instance, s); + // this.o.a(RemoteControlCommandListener.instance, s); return RemoteControlCommandListener.instance.f(); }}; processQueue.add(waitable); @@ -891,12 +905,12 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } public void h(String s) { - h.error(s); + i.error(s); } public void i(String s) { if (this.isDebugging()) { - h.info(s); + i.info(s); } } @@ -910,7 +924,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo crashreport.g().a("Vec3 Pool Size", (Callable) (new CrashReportVec3DPoolSize(this))); } - if (this.t != null) { + if (this.u != null) { crashreport.g().a("Player Count", (Callable) (new CrashReportPlayerCount(this))); } @@ -925,7 +939,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo if (s.startsWith("/")) { s = s.substring(1); boolean flag = !s.contains(" "); - List list = this.n.b(icommandlistener, s); + List list = this.o.b(icommandlistener, s); if (list != null) { Iterator iterator = list.iterator(); @@ -945,7 +959,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } else { String[] astring = s.split(" ", -1); String s2 = astring[astring.length - 1]; - String[] astring1 = this.t.d(); + String[] astring1 = this.u.f(); int i = astring1.length; for (int j = 0; j < i; ++j) { @@ -964,7 +978,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } public static MinecraftServer getServer() { - return i; + return j; } public String getName() { @@ -972,7 +986,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } public void sendMessage(IChatBaseComponent ichatbasecomponent) { - h.info(ichatbasecomponent.c()); + i.info(ichatbasecomponent.c()); } public boolean a(int i, String s) { @@ -980,43 +994,43 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } public ICommandHandler getCommandHandler() { - return this.n; + return this.o; } - public KeyPair J() { - return this.F; + public KeyPair K() { + return this.G; } - public int K() { - return this.s; + public int L() { + return this.t; } public void setPort(int i) { - this.s = i; + this.t = i; } - public String L() { - return this.G; + public String M() { + return this.H; } public void j(String s) { - this.G = s; + this.H = s; } - public boolean M() { - return this.G != null; + public boolean N() { + return this.H != null; } - public String N() { - return this.H; + public String O() { + return this.I; } public void k(String s) { - this.H = s; + this.I = s; } public void a(KeyPair keypair) { - this.F = keypair; + this.G = keypair; } public void a(EnumDifficulty enumdifficulty) { @@ -1029,7 +1043,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo if (worldserver.getWorldData().isHardcore()) { worldserver.difficulty = EnumDifficulty.HARD; worldserver.setSpawnFlags(true, true); - } else if (this.M()) { + } else if (this.N()) { worldserver.difficulty = enumdifficulty; worldserver.setSpawnFlags(worldserver.difficulty != EnumDifficulty.PEACEFUL, true); } else { @@ -1044,7 +1058,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo return true; } - public boolean Q() { + public boolean R() { return this.demoMode; } @@ -1053,15 +1067,15 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } public void c(boolean flag) { - this.K = flag; + this.L = flag; } public Convertable getConvertable() { return this.convertable; } - public void T() { - this.L = true; + public void U() { + this.M = true; this.getConvertable().d(); // CraftBukkit start @@ -1079,11 +1093,11 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } public String getResourcePack() { - return this.M; + return this.N; } public void setTexturePack(String s) { - this.M = s; + this.N = s; } public void a(MojangStatisticsGenerator mojangstatisticsgenerator) { @@ -1091,11 +1105,11 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo mojangstatisticsgenerator.a("whitelist_count", Integer.valueOf(0)); mojangstatisticsgenerator.a("players_current", Integer.valueOf(this.C())); mojangstatisticsgenerator.a("players_max", Integer.valueOf(this.D())); - mojangstatisticsgenerator.a("players_seen", Integer.valueOf(this.t.getSeenPlayers().length)); + mojangstatisticsgenerator.a("players_seen", Integer.valueOf(this.u.getSeenPlayers().length)); mojangstatisticsgenerator.a("uses_auth", Boolean.valueOf(this.onlineMode)); - mojangstatisticsgenerator.a("gui_state", this.aj() ? "enabled" : "disabled"); - mojangstatisticsgenerator.a("run_time", Long.valueOf((aq() - mojangstatisticsgenerator.g()) / 60L * 1000L)); - mojangstatisticsgenerator.a("avg_tick_ms", Integer.valueOf((int) (MathHelper.a(this.f) * 1.0E-6D))); + mojangstatisticsgenerator.a("gui_state", this.ak() ? "enabled" : "disabled"); + mojangstatisticsgenerator.a("run_time", Long.valueOf((ar() - mojangstatisticsgenerator.g()) / 60L * 1000L)); + mojangstatisticsgenerator.a("avg_tick_ms", Integer.valueOf((int) (MathHelper.a(this.g) * 1.0E-6D))); int i = 0; // CraftBukkit start - use worlds list for iteration @@ -1111,7 +1125,7 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo mojangstatisticsgenerator.a("world[" + i + "][hardcore]", Boolean.valueOf(worlddata.isHardcore())); mojangstatisticsgenerator.a("world[" + i + "][generator_name]", worlddata.getType().name()); mojangstatisticsgenerator.a("world[" + i + "][generator_version]", Integer.valueOf(worlddata.getType().getVersion())); - mojangstatisticsgenerator.a("world[" + i + "][height]", Integer.valueOf(this.D)); + mojangstatisticsgenerator.a("world[" + i + "][height]", Integer.valueOf(this.E)); mojangstatisticsgenerator.a("world[" + i + "][chunks_loaded]", Integer.valueOf(worldserver.L().getLoadedChunks())); ++i; } @@ -1121,17 +1135,17 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } public void b(MojangStatisticsGenerator mojangstatisticsgenerator) { - mojangstatisticsgenerator.b("singleplayer", Boolean.valueOf(this.M())); + mojangstatisticsgenerator.b("singleplayer", Boolean.valueOf(this.N())); mojangstatisticsgenerator.b("server_brand", this.getServerModName()); mojangstatisticsgenerator.b("gui_supported", GraphicsEnvironment.isHeadless() ? "headless" : "supported"); - mojangstatisticsgenerator.b("dedicated", Boolean.valueOf(this.W())); + mojangstatisticsgenerator.b("dedicated", Boolean.valueOf(this.X())); } public boolean getSnooperEnabled() { return true; } - public abstract boolean W(); + public abstract boolean X(); public boolean getOnlineMode() { return this.server.getOnlineMode(); // CraftBukkit @@ -1184,11 +1198,11 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } public int getMaxBuildHeight() { - return this.D; + return this.E; } public void c(int i) { - this.D = i; + this.E = i; } public boolean isStopped() { @@ -1196,11 +1210,11 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } public PlayerList getPlayerList() { - return this.t; + return this.u; } public void a(PlayerList playerlist) { - this.t = playerlist; + this.u = playerlist; } public void a(EnumGamemode enumgamemode) { @@ -1211,22 +1225,22 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } } - public ServerConnection ah() { - return this.o; + public ServerConnection ai() { + return this.p; } - public boolean aj() { + public boolean ak() { return false; } public abstract String a(EnumGamemode enumgamemode, boolean flag); - public int ak() { + public int al() { return this.ticks; } - public void al() { - this.Q = true; + public void am() { + this.R = true; } public ChunkCoordinates getChunkCoordinates() { @@ -1246,54 +1260,62 @@ public abstract class MinecraftServer implements ICommandListener, Runnable, IMo } public void setForceGamemode(boolean flag) { - this.R = flag; + this.S = flag; } public boolean getForceGamemode() { - return this.R; + return this.S; } - public Proxy ap() { - return this.c; + public Proxy aq() { + return this.d; } - public static long aq() { + public static long ar() { return System.currentTimeMillis(); } public int getIdleTimeout() { - return this.E; + return this.F; } public void setIdleTimeout(int i) { - this.E = i; + this.F = i; } public IChatBaseComponent getScoreboardDisplayName() { return new ChatComponentText(this.getName()); } - public boolean as() { + public boolean at() { return true; } - public MinecraftSessionService at() { - return this.S; + public MinecraftSessionService av() { + return this.U; } - public ServerPing au() { - return this.p; + public GameProfileRepository getGameProfileRepository() { + return this.W; + } + + public UserCache getUserCache() { + return this.X; + } + + public ServerPing ay() { + return this.q; } - public void av() { - this.T = 0L; + public void az() { + this.V = 0L; } public static Logger getLogger() { - return h; + return i; } public static PlayerList a(MinecraftServer minecraftserver) { - return minecraftserver.t; + return minecraftserver.u; } } diff --git a/src/main/java/net/minecraft/server/NameReferencingFileConverter.java b/src/main/java/net/minecraft/server/NameReferencingFileConverter.java new file mode 100644 index 00000000..01dedf2f --- /dev/null +++ b/src/main/java/net/minecraft/server/NameReferencingFileConverter.java @@ -0,0 +1,410 @@ +package net.minecraft.server; + +import java.io.File; +import java.io.FileNotFoundException; +import java.io.IOException; +import java.text.ParseException; +import java.util.ArrayList; +import java.util.Collection; +import java.util.Date; +import java.util.HashMap; +import java.util.Iterator; +import java.util.List; +import java.util.Locale; +import java.util.Map; +import java.util.UUID; + +import net.minecraft.util.com.google.common.base.Charsets; +import net.minecraft.util.com.google.common.collect.Iterators; +import net.minecraft.util.com.google.common.collect.Lists; +import net.minecraft.util.com.google.common.collect.Maps; +import net.minecraft.util.com.google.common.io.Files; +import net.minecraft.util.com.mojang.authlib.Agent; +import net.minecraft.util.com.mojang.authlib.GameProfile; +import net.minecraft.util.com.mojang.authlib.ProfileLookupCallback; +import org.apache.logging.log4j.LogManager; +import org.apache.logging.log4j.Logger; + +// CraftBukkit - Imported for package private static methods + +public class NameReferencingFileConverter { + + private static final Logger e = LogManager.getLogger(); + public static final File a = new File("banned-ips.txt"); + public static final File b = new File("banned-players.txt"); + public static final File c = new File("ops.txt"); + public static final File d = new File("white-list.txt"); + + static List a(File file1, Map map) throws IOException { // CraftBukkit - Added throws + List list = Files.readLines(file1, Charsets.UTF_8); + Iterator iterator = list.iterator(); + + while (iterator.hasNext()) { + String s = (String) iterator.next(); + + s = s.trim(); + if (!s.startsWith("#") && s.length() >= 1) { + String[] astring = s.split("\\|"); + + map.put(astring[0].toLowerCase(Locale.ROOT), astring); + } + } + + return list; + } + + private static void a(MinecraftServer minecraftserver, Collection collection, ProfileLookupCallback profilelookupcallback) { + String[] astring = (String[]) Iterators.toArray(Iterators.filter(collection.iterator(), new PredicateEmptyList()), String.class); + + if (minecraftserver.getOnlineMode()) { + minecraftserver.getGameProfileRepository().findProfilesByNames(astring, Agent.MINECRAFT, profilelookupcallback); + } else { + String[] astring1 = astring; + int i = astring.length; + + for (int j = 0; j < i; ++j) { + String s = astring1[j]; + UUID uuid = EntityHuman.a(new GameProfile((UUID) null, s)); + GameProfile gameprofile = new GameProfile(uuid, s); + + profilelookupcallback.onProfileLookupSucceeded(gameprofile); + } + } + } + + public static boolean a(MinecraftServer minecraftserver) { + GameProfileBanList gameprofilebanlist = new GameProfileBanList(PlayerList.a); + + if (b.exists() && b.isFile()) { + if (gameprofilebanlist.c().exists()) { + /* CraftBukkit start - Exception is never thrown + try { + gameprofilebanlist.load(); + } catch (FileNotFoundException filenotfoundexception) { + e.warn("Could not load existing file " + gameprofilebanlist.c().getName(), filenotfoundexception); + } + */ + gameprofilebanlist.load(); + // CraftBukkit end + } + + try { + HashMap hashmap = Maps.newHashMap(); + + a(b, (Map) hashmap); + GameProfileBanListEntryConverter gameprofilebanlistentryconverter = new GameProfileBanListEntryConverter(minecraftserver, hashmap, gameprofilebanlist); + + a(minecraftserver, hashmap.keySet(), gameprofilebanlistentryconverter); + gameprofilebanlist.save(); + c(b); + return true; + } catch (IOException ioexception) { + e.warn("Could not read old user banlist to convert it!", ioexception); + return false; + } catch (FileConversionException fileconversionexception) { + e.error("Conversion failed, please try again later", fileconversionexception); + return false; + } + } else { + return true; + } + } + + public static boolean b(MinecraftServer minecraftserver) { + IpBanList ipbanlist = new IpBanList(PlayerList.b); + + if (a.exists() && a.isFile()) { + if (ipbanlist.c().exists()) { + /* CraftBukkit start - Exception is never thrown + try { + ipbanlist.load(); + } catch (FileNotFoundException filenotfoundexception) { + e.warn("Could not load existing file " + ipbanlist.c().getName(), filenotfoundexception); + } + */ + ipbanlist.load(); + // CraftBukkit end + } + + try { + HashMap hashmap = Maps.newHashMap(); + + a(a, (Map) hashmap); + Iterator iterator = hashmap.keySet().iterator(); + + while (iterator.hasNext()) { + String s = (String) iterator.next(); + String[] astring = (String[]) hashmap.get(s); + Date date = astring.length > 1 ? b(astring[1], (Date) null) : null; + String s1 = astring.length > 2 ? astring[2] : null; + Date date1 = astring.length > 3 ? b(astring[3], (Date) null) : null; + String s2 = astring.length > 4 ? astring[4] : null; + + ipbanlist.add(new IpBanEntry(s, date, s1, date1, s2)); + } + + ipbanlist.save(); + c(a); + return true; + } catch (IOException ioexception) { + e.warn("Could not parse old ip banlist to convert it!", ioexception); + return false; + } + } else { + return true; + } + } + + public static boolean c(MinecraftServer minecraftserver) { + OpList oplist = new OpList(PlayerList.c); + + if (c.exists() && c.isFile()) { + if (oplist.c().exists()) { + /* CraftBukkit start - Exception is never thrown + try { + oplist.load(); + } catch (FileNotFoundException filenotfoundexception) { + e.warn("Could not load existing file " + oplist.c().getName(), filenotfoundexception); + } + */ + oplist.load(); + // CraftBukkit end + } + + try { + List list = Files.readLines(c, Charsets.UTF_8); + OpListProfileCallback oplistprofilecallback = new OpListProfileCallback(minecraftserver, oplist); + + a(minecraftserver, list, oplistprofilecallback); + oplist.save(); + c(c); + return true; + } catch (IOException ioexception) { + e.warn("Could not read old oplist to convert it!", ioexception); + return false; + } catch (FileConversionException fileconversionexception) { + e.error("Conversion failed, please try again later", fileconversionexception); + return false; + } + } else { + return true; + } + } + + public static boolean d(MinecraftServer minecraftserver) { + WhiteList whitelist = new WhiteList(PlayerList.d); + + if (d.exists() && d.isFile()) { + if (whitelist.c().exists()) { + /* CraftBukkit start - Exception is never thrown + try { + whitelist.load(); + } catch (FileNotFoundException filenotfoundexception) { + e.warn("Could not load existing file " + whitelist.c().getName(), filenotfoundexception); + } + */ + whitelist.load(); + // CraftBukkit end + } + + try { + List list = Files.readLines(d, Charsets.UTF_8); + WhiteListProfileCallback whitelistprofilecallback = new WhiteListProfileCallback(minecraftserver, whitelist); + + a(minecraftserver, list, whitelistprofilecallback); + whitelist.save(); + c(d); + return true; + } catch (IOException ioexception) { + e.warn("Could not read old whitelist to convert it!", ioexception); + return false; + } catch (FileConversionException fileconversionexception) { + e.error("Conversion failed, please try again later", fileconversionexception); + return false; + } + } else { + return true; + } + } + + public static String a(String s) { + if (!UtilColor.b(s) && s.length() <= 16) { + MinecraftServer minecraftserver = MinecraftServer.getServer(); + GameProfile gameprofile = minecraftserver.getUserCache().a(s); + + if (gameprofile != null && gameprofile.getId() != null) { + return gameprofile.getId().toString(); + } else if (!minecraftserver.N() && minecraftserver.getOnlineMode()) { + ArrayList arraylist = Lists.newArrayList(); + GameProfileLookupCallback gameprofilelookupcallback = new GameProfileLookupCallback(minecraftserver, arraylist); + + a(minecraftserver, Lists.newArrayList(new String[] { s}), gameprofilelookupcallback); + return arraylist.size() > 0 && ((GameProfile) arraylist.get(0)).getId() != null ? ((GameProfile) arraylist.get(0)).getId().toString() : ""; + } else { + return EntityHuman.a(new GameProfile((UUID) null, s)).toString(); + } + } else { + return s; + } + } + + public static boolean a(DedicatedServer dedicatedserver, PropertyManager propertymanager) { + File file1 = d(propertymanager); + File file2 = new File(file1.getParentFile(), "playerdata"); + File file3 = new File(file1.getParentFile(), "unknownplayers"); + + if (file1.exists() && file1.isDirectory()) { + File[] afile = file1.listFiles(); + ArrayList arraylist = Lists.newArrayList(); + File[] afile1 = afile; + int i = afile.length; + + for (int j = 0; j < i; ++j) { + File file4 = afile1[j]; + String s = file4.getName(); + + if (s.toLowerCase(Locale.ROOT).endsWith(".dat")) { + String s1 = s.substring(0, s.length() - ".dat".length()); + + if (s1.length() > 0) { + arraylist.add(s1); + } + } + } + + try { + String[] astring = (String[]) arraylist.toArray(new String[arraylist.size()]); + PlayerDatFileConverter playerdatfileconverter = new PlayerDatFileConverter(dedicatedserver, file2, file3, file1, astring); + + a(dedicatedserver, Lists.newArrayList(astring), playerdatfileconverter); + return true; + } catch (FileConversionException fileconversionexception) { + e.error("Conversion failed, please try again later", fileconversionexception); + return false; + } + } else { + return true; + } + } + + private static void b(File file1) { + if (file1.exists()) { + if (!file1.isDirectory()) { + throw new FileConversionException("Can\'t create directory " + file1.getName() + " in world save directory.", (PredicateEmptyList) null); + } + } else if (!file1.mkdirs()) { + throw new FileConversionException("Can\'t create directory " + file1.getName() + " in world save directory.", (PredicateEmptyList) null); + } + } + + public static boolean a(PropertyManager propertymanager) { + boolean flag = b(propertymanager); + + flag = flag && c(propertymanager); + return flag; + } + + private static boolean b(PropertyManager propertymanager) { + boolean flag = false; + + if (b.exists() && b.isFile()) { + flag = true; + } + + boolean flag1 = false; + + if (a.exists() && a.isFile()) { + flag1 = true; + } + + boolean flag2 = false; + + if (c.exists() && c.isFile()) { + flag2 = true; + } + + boolean flag3 = false; + + if (d.exists() && d.isFile()) { + flag3 = true; + } + + if (!flag && !flag1 && !flag2 && !flag3) { + return true; + } else { + e.warn("**** FAILED TO START THE SERVER AFTER ACCOUNT CONVERSION!"); + e.warn("** please remove the following files and restart the server:"); + if (flag) { + e.warn("* " + b.getName()); + } + + if (flag1) { + e.warn("* " + a.getName()); + } + + if (flag2) { + e.warn("* " + c.getName()); + } + + if (flag3) { + e.warn("* " + d.getName()); + } + + return false; + } + } + + private static boolean c(PropertyManager propertymanager) { + File file1 = d(propertymanager); + + if (file1.exists() && file1.isDirectory()) { + String[] astring = file1.list(new DatFilenameFilter()); + + if (astring.length > 0) { + e.warn("**** DETECTED OLD PLAYER FILES IN THE WORLD SAVE"); + e.warn("**** THIS USUALLY HAPPENS WHEN THE AUTOMATIC CONVERSION FAILED IN SOME WAY"); + e.warn("** please restart the server and if the problem persists, remove the directory \'{}\'", new Object[] { file1.getPath()}); + return false; + } + } + + return true; + } + + private static File d(PropertyManager propertymanager) { + String s = propertymanager.getString("level-name", "world"); + File file1 = new File(s); + + return new File(file1, "players"); + } + + private static void c(File file1) { + File file2 = new File(file1.getName() + ".converted"); + + file1.renameTo(file2); + } + + private static Date b(String s, Date date) { + Date date1; + + try { + date1 = ExpirableListEntry.a.parse(s); + } catch (ParseException parseexception) { + date1 = date; + } + + return date1; + } + + static Logger a() { + return e; + } + + static Date a(String s, Date date) { + return b(s, date); + } + + static void a(File file1) { + b(file1); + } +} diff --git a/src/main/java/net/minecraft/server/NetworkManager.java b/src/main/java/net/minecraft/server/NetworkManager.java index 9ff1694d..1dd22279 100644 --- a/src/main/java/net/minecraft/server/NetworkManager.java +++ b/src/main/java/net/minecraft/server/NetworkManager.java @@ -40,6 +40,7 @@ public class NetworkManager extends SimpleChannelInboundHandler { private PacketListener o; private EnumProtocol p; private IChatBaseComponent q; + private boolean r; public NetworkManager(boolean flag) { this.j = flag; @@ -86,7 +87,7 @@ public class NetworkManager extends SimpleChannelInboundHandler { public void handle(Packet packet, GenericFutureListener... agenericfuturelistener) { if (this.m != null && this.m.isOpen()) { - this.h(); + this.i(); this.b(packet, agenericfuturelistener); } else { this.l.add(new QueuedPacket(packet, agenericfuturelistener)); @@ -113,7 +114,7 @@ public class NetworkManager extends SimpleChannelInboundHandler { } } - private void h() { + private void i() { if (this.m != null && this.m.isOpen()) { while (!this.l.isEmpty()) { QueuedPacket queuedpacket = (QueuedPacket) this.l.poll(); @@ -124,7 +125,7 @@ public class NetworkManager extends SimpleChannelInboundHandler { } public void a() { - this.h(); + this.i(); EnumProtocol enumprotocol = (EnumProtocol) this.m.attr(d).get(); if (this.p != enumprotocol) { @@ -171,6 +172,7 @@ public class NetworkManager extends SimpleChannelInboundHandler { public void a(SecretKey secretkey) { this.m.pipeline().addBefore("splitter", "decrypt", new PacketDecrypter(MinecraftEncryption.a(2, secretkey))); this.m.pipeline().addBefore("prepender", "encrypt", new PacketEncrypter(MinecraftEncryption.a(1, secretkey))); + this.r = true; } public boolean isConnected() { diff --git a/src/main/java/net/minecraft/server/PacketDataSerializer.java b/src/main/java/net/minecraft/server/PacketDataSerializer.java index fe2b24d3..f6f870fd 100644 --- a/src/main/java/net/minecraft/server/PacketDataSerializer.java +++ b/src/main/java/net/minecraft/server/PacketDataSerializer.java @@ -74,7 +74,7 @@ public class PacketDataSerializer extends ByteBuf { byte[] abyte = new byte[short1]; this.readBytes(abyte); - return NBTCompressedStreamTools.a(abyte); + return NBTCompressedStreamTools.a(abyte, new NBTReadLimiter(2097152L)); } } diff --git a/src/main/java/net/minecraft/server/PacketPlayOutNamedEntitySpawn.java b/src/main/java/net/minecraft/server/PacketPlayOutNamedEntitySpawn.java index 8bab5281..7bae4054 100644 --- a/src/main/java/net/minecraft/server/PacketPlayOutNamedEntitySpawn.java +++ b/src/main/java/net/minecraft/server/PacketPlayOutNamedEntitySpawn.java @@ -1,8 +1,11 @@ package net.minecraft.server; +import java.util.Iterator; import java.util.List; +import java.util.UUID; import net.minecraft.util.com.mojang.authlib.GameProfile; +import net.minecraft.util.com.mojang.authlib.properties.Property; import java.io.IOException; // CraftBukkit @@ -37,7 +40,19 @@ public class PacketPlayOutNamedEntitySpawn extends Packet { public void a(PacketDataSerializer packetdataserializer) throws IOException { // CraftBukkit - added throws this.a = packetdataserializer.a(); - this.b = new GameProfile(packetdataserializer.c(36), packetdataserializer.c(16)); + UUID uuid = UUID.fromString(packetdataserializer.c(36)); + + this.b = new GameProfile(uuid, packetdataserializer.c(16)); + int i = packetdataserializer.a(); + + for (int j = 0; j < i; ++j) { + String s = packetdataserializer.c(32767); + String s1 = packetdataserializer.c(32767); + String s2 = packetdataserializer.c(32767); + + this.b.getProperties().put(s, new Property(s, s1, s2)); + } + this.c = packetdataserializer.readInt(); this.d = packetdataserializer.readInt(); this.e = packetdataserializer.readInt(); @@ -49,8 +64,21 @@ public class PacketPlayOutNamedEntitySpawn extends Packet { public void b(PacketDataSerializer packetdataserializer) throws IOException { // CraftBukkit - added throws packetdataserializer.b(this.a); - packetdataserializer.a(this.b.getId()); + UUID uuid = this.b.getId(); + + packetdataserializer.a(uuid == null ? "" : uuid.toString()); packetdataserializer.a(this.b.getName().length() > 16 ? this.b.getName().substring(0, 16) : this.b.getName()); // CraftBukkit - Limit name length to 16 characters + packetdataserializer.b(this.b.getProperties().size()); + Iterator iterator = this.b.getProperties().values().iterator(); + + while (iterator.hasNext()) { + Property property = (Property) iterator.next(); + + packetdataserializer.a(property.getName()); + packetdataserializer.a(property.getValue()); + packetdataserializer.a(property.getSignature()); + } + packetdataserializer.writeInt(this.c); packetdataserializer.writeInt(this.d); packetdataserializer.writeInt(this.e); diff --git a/src/main/java/net/minecraft/server/PacketStatusListener.java b/src/main/java/net/minecraft/server/PacketStatusListener.java index 7903c438..cd063053 100644 --- a/src/main/java/net/minecraft/server/PacketStatusListener.java +++ b/src/main/java/net/minecraft/server/PacketStatusListener.java @@ -116,7 +116,7 @@ public class PacketStatusListener implements PacketStatusInListener { ping.setFavicon(event.icon.value); ping.setMOTD(new ChatComponentText(event.getMotd())); ping.setPlayerSample(playerSample); - ping.setServerInfo(new ServerPingServerData(minecraftServer.getServerModName() + " " + minecraftServer.getVersion(), 4)); // TODO: Update when protocol changes + ping.setServerInfo(new ServerPingServerData(minecraftServer.getServerModName() + " " + minecraftServer.getVersion(), 5)); // TODO: Update when protocol changes this.networkManager.handle(new PacketStatusOutServerInfo(ping), new GenericFutureListener[0]); // CraftBukkit end diff --git a/src/main/java/net/minecraft/server/PathfinderGoalTarget.java b/src/main/java/net/minecraft/server/PathfinderGoalTarget.java index 84122eb7..ebc19407 100644 --- a/src/main/java/net/minecraft/server/PathfinderGoalTarget.java +++ b/src/main/java/net/minecraft/server/PathfinderGoalTarget.java @@ -78,8 +78,8 @@ public abstract class PathfinderGoalTarget extends PathfinderGoal { } else if (!this.c.a(entityliving.getClass())) { return false; } else { - if (this.c instanceof EntityOwnable && StringUtils.isNotEmpty(((EntityOwnable) this.c).getOwnerName())) { - if (entityliving instanceof EntityOwnable && ((EntityOwnable) this.c).getOwnerName().equals(((EntityOwnable) entityliving).getOwnerName())) { + if (this.c instanceof EntityOwnable && StringUtils.isNotEmpty(((EntityOwnable) this.c).getOwnerUUID())) { + if (entityliving instanceof EntityOwnable && ((EntityOwnable) this.c).getOwnerUUID().equals(((EntityOwnable) entityliving).getOwnerUUID())) { return false; } diff --git a/src/main/java/net/minecraft/server/PlayerChunkMap.java b/src/main/java/net/minecraft/server/PlayerChunkMap.java index 90776db4..ae53635d 100644 --- a/src/main/java/net/minecraft/server/PlayerChunkMap.java +++ b/src/main/java/net/minecraft/server/PlayerChunkMap.java @@ -28,7 +28,7 @@ public class PlayerChunkMap { public PlayerChunkMap(WorldServer worldserver) { this.world = worldserver; - this.a(worldserver.getMinecraftServer().getPlayerList().o()); + this.a(worldserver.getMinecraftServer().getPlayerList().s()); } public WorldServer a() { diff --git a/src/main/java/net/minecraft/server/PlayerConnection.java b/src/main/java/net/minecraft/server/PlayerConnection.java index be2bca23..946681d3 100644 --- a/src/main/java/net/minecraft/server/PlayerConnection.java +++ b/src/main/java/net/minecraft/server/PlayerConnection.java @@ -4,6 +4,7 @@ import java.io.ByteArrayInputStream; import java.io.DataInputStream; import java.io.IOException; import java.util.ArrayList; +import java.util.Date; import java.util.Iterator; import java.util.Random; import java.util.concurrent.Callable; @@ -356,7 +357,7 @@ public class PlayerConnection implements PacketPlayInListener { // CraftBukkit end double d10 = d7 * d7 + d8 * d8 + d9 * d9; - if (d10 > 100.0D && this.checkMovement && (!this.minecraftServer.M() || !this.minecraftServer.L().equals(this.player.getName()))) { // CraftBukkit - Added this.checkMovement condition to solve this check being triggered by teleports + if (d10 > 100.0D && this.checkMovement && (!this.minecraftServer.N() || !this.minecraftServer.M().equals(this.player.getName()))) { // CraftBukkit - Added this.checkMovement condition to solve this check being triggered by teleports c.warn(this.player.getName() + " moved too quickly! " + d4 + "," + d5 + "," + d6 + " (" + d7 + ", " + d8 + ", " + d9 + ")"); this.a(this.y, this.z, this.q, this.player.yaw, this.player.pitch); return; @@ -689,7 +690,7 @@ public class PlayerConnection implements PacketPlayInListener { } // CraftBukkit end c.info(this.player.getName() + " lost connection: " + ichatbasecomponent.c()); // CraftBukkit - Don't toString the component - this.minecraftServer.av(); + this.minecraftServer.az(); // CraftBukkit start - Replace vanilla quit message handling with our own. /* ChatMessage chatmessage = new ChatMessage("multiplayer.player.left", new Object[] { this.player.getScoreboardDisplayName()}); @@ -704,7 +705,7 @@ public class PlayerConnection implements PacketPlayInListener { this.minecraftServer.getPlayerList().sendMessage(CraftChatMessage.fromString(quitMessage)); } // CraftBukkit end - if (this.minecraftServer.M() && this.player.getName().equals(this.minecraftServer.L())) { + if (this.minecraftServer.N() && this.player.getName().equals(this.minecraftServer.M())) { c.info("Stopping singleplayer server as player logged out"); this.minecraftServer.safeShutdown(); } @@ -835,7 +836,7 @@ public class PlayerConnection implements PacketPlayInListener { // CraftBukkit start - replaced with thread safe throttle // this.chatThrottle += 20; - if (chatSpamField.addAndGet(this, 20) > 200 && !this.minecraftServer.getPlayerList().isOp(this.player.getName())) { + if (chatSpamField.addAndGet(this, 20) > 200 && !this.minecraftServer.getPlayerList().isOp(this.player.getProfile())) { if (packetplayinchat.a()) { Waitable waitable = new Waitable() { @Override @@ -1120,14 +1121,13 @@ public class PlayerConnection implements PacketPlayInListener { if (this.player.viewingCredits) { this.minecraftServer.getPlayerList().changeDimension(this.player, 0, PlayerTeleportEvent.TeleportCause.END_PORTAL); // CraftBukkit - reroute logic through custom portal management } else if (this.player.r().getWorldData().isHardcore()) { - if (this.minecraftServer.M() && this.player.getName().equals(this.minecraftServer.L())) { + if (this.minecraftServer.N() && this.player.getName().equals(this.minecraftServer.M())) { this.player.playerConnection.disconnect("You have died. Game over, man, it\'s game over!"); - this.minecraftServer.T(); + this.minecraftServer.U(); } else { - BanEntry banentry = new BanEntry(this.player.getName()); + GameProfileBanEntry gameprofilebanentry = new GameProfileBanEntry(this.player.getProfile(), (Date) null, "(You just lost the game)", (Date) null, "Death in Hardcore"); - banentry.setReason("Death in Hardcore"); - this.minecraftServer.getPlayerList().getNameBans().add(banentry); + this.minecraftServer.getPlayerList().getProfileBans().add(gameprofilebanentry); this.player.playerConnection.disconnect("You have died. Game over, man, it\'s game over!"); } } else { @@ -1654,16 +1654,16 @@ public class PlayerConnection implements PacketPlayInListener { try { itemstack = packetdataserializer.c(); - if (itemstack != null) { - if (!ItemBookAndQuill.a(itemstack.getTag())) { - throw new IOException("Invalid book tag!"); - } + if (itemstack == null) { + return; + } - itemstack1 = this.player.inventory.getItemInHand(); - if (itemstack1 == null) { - return; - } + if (!ItemBookAndQuill.a(itemstack.getTag())) { + throw new IOException("Invalid book tag!"); + } + itemstack1 = this.player.inventory.getItemInHand(); + if (itemstack1 != null) { if (itemstack.getItem() == Items.BOOK_AND_QUILL && itemstack.getItem() == itemstack1.getItem()) { itemstack1.a("pages", (NBTBase) itemstack.getTag().getList("pages", 8)); } @@ -1686,18 +1686,18 @@ public class PlayerConnection implements PacketPlayInListener { try { itemstack = packetdataserializer.c(); - if (itemstack == null) { - return; - } + if (itemstack != null) { + if (!ItemWrittenBook.a(itemstack.getTag())) { + throw new IOException("Invalid book tag!"); + } - if (!ItemWrittenBook.a(itemstack.getTag())) { - throw new IOException("Invalid book tag!"); - } + itemstack1 = this.player.inventory.getItemInHand(); + if (itemstack1 == null) { + return; + } - itemstack1 = this.player.inventory.getItemInHand(); - if (itemstack1 != null) { if (itemstack.getItem() == Items.WRITTEN_BOOK && itemstack1.getItem() == Items.BOOK_AND_QUILL) { - CraftEventFactory.handleEditBookEvent(player, itemstack); // CraftBukkit + CraftEventFactory.handleEditBookEvent(player, itemstack); // CraftBukkit } return; diff --git a/src/main/java/net/minecraft/server/PlayerDatFileConverter.java b/src/main/java/net/minecraft/server/PlayerDatFileConverter.java new file mode 100644 index 00000000..27651b5a --- /dev/null +++ b/src/main/java/net/minecraft/server/PlayerDatFileConverter.java @@ -0,0 +1,98 @@ +package net.minecraft.server; + +import java.io.File; +import java.util.UUID; + +import net.minecraft.util.com.mojang.authlib.GameProfile; +import net.minecraft.util.com.mojang.authlib.ProfileLookupCallback; +import net.minecraft.util.com.mojang.authlib.yggdrasil.ProfileNotFoundException; + +final class PlayerDatFileConverter implements ProfileLookupCallback { + + final DedicatedServer a; + final File b; + final File c; + final File d; + final String[] e; + + PlayerDatFileConverter(DedicatedServer dedicatedserver, File file1, File file2, File file3, String[] astring) { + this.a = dedicatedserver; + this.b = file1; + this.c = file2; + this.d = file3; + this.e = astring; + } + + public void onProfileLookupSucceeded(GameProfile gameprofile) { + this.a.getUserCache().a(gameprofile); + UUID uuid = gameprofile.getId(); + + if (uuid == null) { + throw new FileConversionException("Missing UUID for user profile " + gameprofile.getName(), (PredicateEmptyList) null); + } else { + this.a(this.b, this.a(gameprofile), uuid.toString()); + } + } + + public void onProfileLookupFailed(GameProfile gameprofile, Exception exception) { + NameReferencingFileConverter.a().warn("Could not lookup user uuid for " + gameprofile.getName(), exception); + if (exception instanceof ProfileNotFoundException) { + String s = this.a(gameprofile); + + this.a(this.c, s, s); + } else { + throw new FileConversionException("Could not request user " + gameprofile.getName() + " from backend systems", exception, (PredicateEmptyList) null); + } + } + + private void a(File file1, String s, String s1) { + File file2 = new File(this.d, s + ".dat"); + File file3 = new File(file1, s1 + ".dat"); + + // CraftBukkit start - Use old file name to seed lastKnownName + NBTTagCompound root = null; + + try { + root = NBTCompressedStreamTools.a(new java.io.FileInputStream(file2)); + } catch (Exception exception) { + exception.printStackTrace(); + } + + if (root != null) { + if (!root.hasKey("bukkit")) { + root.set("bukkit", new NBTTagCompound()); + } + NBTTagCompound data = root.getCompound("bukkit"); + data.setString("lastKnownName", s); + + try { + NBTCompressedStreamTools.a(root, new java.io.FileOutputStream(file2)); + } catch (Exception exception) { + exception.printStackTrace(); + } + } + // CraftBukkit end + + NameReferencingFileConverter.a(file1); + if (!file2.renameTo(file3)) { + throw new FileConversionException("Could not convert file for " + s, (PredicateEmptyList) null); + } + } + + private String a(GameProfile gameprofile) { + String s = null; + + for (int i = 0; i < this.e.length; ++i) { + if (this.e[i] != null && this.e[i].equalsIgnoreCase(gameprofile.getName())) { + s = this.e[i]; + break; + } + } + + if (s == null) { + throw new FileConversionException("Could not find the filename for " + gameprofile.getName() + " anymore", (PredicateEmptyList) null); + } else { + return s; + } + } +} diff --git a/src/main/java/net/minecraft/server/PlayerList.java b/src/main/java/net/minecraft/server/PlayerList.java index 5b0590e7..7c01595f 100644 --- a/src/main/java/net/minecraft/server/PlayerList.java +++ b/src/main/java/net/minecraft/server/PlayerList.java @@ -9,10 +9,11 @@ import java.util.HashSet; import java.util.Iterator; import java.util.List; import java.util.Map; -import java.util.Set; +import java.util.UUID; import java.util.Map.Entry; import net.minecraft.util.com.google.common.base.Charsets; +import net.minecraft.util.com.google.common.collect.Lists; import net.minecraft.util.com.google.common.collect.Maps; import net.minecraft.util.com.mojang.authlib.GameProfile; import org.apache.logging.log4j.LogManager; @@ -39,22 +40,26 @@ import org.bukkit.util.Vector; public abstract class PlayerList { - private static final Logger c = LogManager.getLogger(); - private static final SimpleDateFormat d = new SimpleDateFormat("yyyy-MM-dd \'at\' HH:mm:ss z"); + public static final File a = new File("banned-players.json"); + public static final File b = new File("banned-ips.json"); + public static final File c = new File("ops.json"); + public static final File d = new File("whitelist.json"); + private static final Logger g = LogManager.getLogger(); + private static final SimpleDateFormat h = new SimpleDateFormat("yyyy-MM-dd \'at\' HH:mm:ss z"); private final MinecraftServer server; public final List players = new java.util.concurrent.CopyOnWriteArrayList(); // CraftBukkit - ArrayList -> CopyOnWriteArrayList: Iterator safety - private final BanList banByName = new BanList(new File("banned-players.txt")); - private final BanList banByIP = new BanList(new File("banned-ips.txt")); - private final Set operators = new HashSet(); - private final Set whitelist = new java.util.LinkedHashSet(); // CraftBukkit - HashSet -> LinkedHashSet - private final Map j = Maps.newHashMap(); + private final GameProfileBanList j; + private final IpBanList k; + private final OpList operators; + private final WhiteList whitelist; + private final Map n; public IPlayerFileData playerFileData; // CraftBukkit - private -> public public boolean hasWhitelist; // CraftBukkit - private -> public protected int maxPlayers; - protected int m; - private EnumGamemode n; - private boolean o; - private int p; + private int q; + private EnumGamemode r; + private boolean s; + private int t; // CraftBukkit start private CraftServer cserver; @@ -66,25 +71,36 @@ public abstract class PlayerList { this.cserver = minecraftserver.server; // CraftBukkit end + this.j = new GameProfileBanList(a); + this.k = new IpBanList(b); + this.operators = new OpList(c); + this.whitelist = new WhiteList(d); + this.n = Maps.newHashMap(); this.server = minecraftserver; - this.banByName.setEnabled(false); - this.banByIP.setEnabled(false); + this.j.a(false); + this.k.a(false); this.maxPlayers = 8; } public void a(NetworkManager networkmanager, EntityPlayer entityplayer) { + GameProfile gameprofile = entityplayer.getProfile(); + UserCache usercache = this.server.getUserCache(); + GameProfile gameprofile1 = usercache.a(gameprofile.getId()); + String s = gameprofile1 == null ? gameprofile.getName() : gameprofile1.getName(); + + usercache.a(gameprofile); NBTTagCompound nbttagcompound = this.a(entityplayer); entityplayer.spawnIn(this.server.getWorldServer(entityplayer.dimension)); entityplayer.playerInteractManager.a((WorldServer) entityplayer.world); - String s = "local"; + String s1 = "local"; if (networkmanager.getSocketAddress() != null) { - s = networkmanager.getSocketAddress().toString(); + s1 = networkmanager.getSocketAddress().toString(); } // CraftBukkit - Moved message to after join - // c.info(entityplayer.getName() + "[" + s + "] logged in with entity id " + entityplayer.getId() + " at (" + entityplayer.locX + ", " + entityplayer.locY + ", " + entityplayer.locZ + ")"); + // g.info(entityplayer.getName() + "[" + s1 + "] logged in with entity id " + entityplayer.getId() + " at (" + entityplayer.locX + ", " + entityplayer.locY + ", " + entityplayer.locZ + ")"); WorldServer worldserver = this.server.getWorldServer(entityplayer.dimension); ChunkCoordinates chunkcoordinates = worldserver.getSpawn(); @@ -106,13 +122,19 @@ public abstract class PlayerList { entityplayer.getStatisticManager().d(); entityplayer.getStatisticManager().updateStatistics(entityplayer); this.a((ScoreboardServer) worldserver.getScoreboard(), entityplayer); - this.server.av(); + this.server.az(); /* CraftBukkit start - login message is handled in the event - ChatMessage chatmessage = new ChatMessage("multiplayer.player.joined", new Object[] { entityplayer.getScoreboardDisplayName()}); + ChatMessage chatmessage; + + if (!entityplayer.getName().equalsIgnoreCase(s)) { + chatmessage = new ChatMessage("multiplayer.player.joined.renamed", new Object[] { entityplayer.getScoreboardDisplayName(), s}); + } else { + chatmessage = new ChatMessage("multiplayer.player.joined", new Object[] { entityplayer.getScoreboardDisplayName()}); + } chatmessage.getChatModifier().setColor(EnumChatFormat.YELLOW); this.sendMessage(chatmessage); - // CraftBukkit end*/ + // CraftBukkit end */ this.c(entityplayer); worldserver = this.server.getWorldServer(entityplayer.dimension); // CraftBukkit - Update in case join event changed it playerconnection.a(entityplayer.locX, entityplayer.locY, entityplayer.locZ, entityplayer.yaw, entityplayer.pitch); @@ -142,7 +164,7 @@ public abstract class PlayerList { } // CraftBukkit - Moved from above, added world - c.info(entityplayer.getName() + "[" + s + "] logged in with entity id " + entityplayer.getId() + " at ([" + entityplayer.world.worldData.getName() + "] " + entityplayer.locX + ", " + entityplayer.locY + ", " + entityplayer.locZ + ")"); + g.info(entityplayer.getName() + "[" + s + "] logged in with entity id " + entityplayer.getId() + " at ([" + entityplayer.world.worldData.getName() + "] " + entityplayer.locX + ", " + entityplayer.locY + ", " + entityplayer.locZ + ")"); } public void a(ScoreboardServer scoreboardserver, EntityPlayer entityplayer) { // CraftBukkit - protected -> public @@ -189,8 +211,8 @@ public abstract class PlayerList { worldserver1.chunkProviderServer.getChunkAt((int) entityplayer.locX >> 4, (int) entityplayer.locZ >> 4); } - public int a() { - return PlayerChunkMap.getFurthestViewableBlock(this.o()); + public int d() { + return PlayerChunkMap.getFurthestViewableBlock(this.s()); } public NBTTagCompound a(EntityPlayer entityplayer) { @@ -198,10 +220,10 @@ public abstract class PlayerList { NBTTagCompound nbttagcompound = this.server.worlds.get(0).getWorldData().i(); NBTTagCompound nbttagcompound1; - if (entityplayer.getName().equals(this.server.L()) && nbttagcompound != null) { + if (entityplayer.getName().equals(this.server.M()) && nbttagcompound != null) { entityplayer.f(nbttagcompound); nbttagcompound1 = nbttagcompound; - c.debug("loading single player"); + g.debug("loading single player"); } else { nbttagcompound1 = this.playerFileData.load(entityplayer); } @@ -211,7 +233,7 @@ public abstract class PlayerList { protected void b(EntityPlayer entityplayer) { this.playerFileData.save(entityplayer); - ServerStatisticManager serverstatisticmanager = (ServerStatisticManager) this.j.get(entityplayer.getName()); + ServerStatisticManager serverstatisticmanager = (ServerStatisticManager) this.n.get(entityplayer.getUniqueID()); if (serverstatisticmanager != null) { serverstatisticmanager.b(); @@ -285,18 +307,19 @@ public abstract class PlayerList { this.cserver.getPluginManager().callEvent(playerQuitEvent); entityplayer.getBukkitEntity().disconnect(playerQuitEvent.getQuitMessage()); // CraftBukkit end + this.b(entityplayer); WorldServer worldserver = entityplayer.r(); if (entityplayer.vehicle != null && !(entityplayer.vehicle instanceof EntityPlayer)) { // CraftBukkit - Don't remove players worldserver.removeEntity(entityplayer.vehicle); - c.debug("removing player mount"); + g.debug("removing player mount"); } worldserver.kill(entityplayer); worldserver.getPlayerChunkMap().removePlayer(entityplayer); this.players.remove(entityplayer); - this.j.remove(entityplayer.getName()); + this.n.remove(entityplayer.getUniqueID()); ChunkIOExecutor.adjustPoolSize(this.getPlayerCount()); // CraftBukkit // CraftBukkit start - .name -> .listName, replace sendAll with loop @@ -307,6 +330,8 @@ public abstract class PlayerList { if (entityplayer1.getBukkitEntity().canSee(entityplayer.getBukkitEntity())) { entityplayer1.playerConnection.sendPacket(packet); + } else { + entityplayer1.getBukkitEntity().removeDisconnectingPlayer(entityplayer.getBukkitEntity()); } } // This removes the scoreboard (and player reference) for the specific player in the manager @@ -326,40 +351,35 @@ public abstract class PlayerList { EntityPlayer entity = new EntityPlayer(this.server, this.server.getWorldServer(0), gameprofile, new PlayerInteractManager(this.server.getWorldServer(0))); Player player = entity.getBukkitEntity(); PlayerLoginEvent event = new PlayerLoginEvent(player, hostname, ((java.net.InetSocketAddress) socketaddress).getAddress()); + String s; - if (this.banByName.isBanned(gameprofile.getName())) { - BanEntry banentry = (BanEntry) this.banByName.getEntries().get(gameprofile.getName()); - String s = "You are banned from this server!\nReason: " + banentry.getReason(); + if (this.j.isBanned(gameprofile)) { + GameProfileBanEntry gameprofilebanentry = (GameProfileBanEntry) this.j.get(gameprofile); - if (banentry.getExpires() != null) { - s = s + "\nYour ban will be removed on " + d.format(banentry.getExpires()); + s = "You are banned from this server!\nReason: " + gameprofilebanentry.getReason(); + if (gameprofilebanentry.getExpires() != null) { + s = s + "\nYour ban will be removed on " + h.format(gameprofilebanentry.getExpires()); } // return s; event.disallow(PlayerLoginEvent.Result.KICK_BANNED, s); - } else if (!this.isWhitelisted(gameprofile.getName())) { + } else if (!this.isWhitelisted(gameprofile)) { // return "You are not white-listed on this server!"; event.disallow(PlayerLoginEvent.Result.KICK_WHITELIST, "You are not white-listed on this server!"); - } else { - String s1 = socketaddress.toString(); - - s1 = s1.substring(s1.indexOf("/") + 1); - s1 = s1.substring(0, s1.indexOf(":")); - if (this.banByIP.isBanned(s1)) { - BanEntry banentry1 = (BanEntry) this.banByIP.getEntries().get(s1); - String s2 = "Your IP address is banned from this server!\nReason: " + banentry1.getReason(); + } else if (this.k.isBanned(socketaddress)) { + IpBanEntry ipbanentry = this.k.get(socketaddress); - if (banentry1.getExpires() != null) { - s2 = s2 + "\nYour ban will be removed on " + d.format(banentry1.getExpires()); - } + s = "Your IP address is banned from this server!\nReason: " + ipbanentry.getReason(); + if (ipbanentry.getExpires() != null) { + s = s + "\nYour ban will be removed on " + h.format(ipbanentry.getExpires()); + } - // return s2; - event.disallow(PlayerLoginEvent.Result.KICK_BANNED, s2); - } else { - // return this.players.size() >= this.maxPlayers ? "The server is full!" : null; - if (this.players.size() >= this.maxPlayers) { - event.disallow(PlayerLoginEvent.Result.KICK_FULL, "The server is full!"); - } + // return s2; + event.disallow(PlayerLoginEvent.Result.KICK_BANNED, s); + } else { + // return this.players.size() >= this.maxPlayers ? "The server is full!" : null; + if (this.players.size() >= this.maxPlayers) { + event.disallow(PlayerLoginEvent.Result.KICK_FULL, "The server is full!"); } } @@ -374,13 +394,14 @@ public abstract class PlayerList { } public EntityPlayer processLogin(GameProfile gameprofile, EntityPlayer player) { // CraftBukkit - added EntityPlayer - ArrayList arraylist = new ArrayList(); + UUID uuid = EntityHuman.a(gameprofile); + ArrayList arraylist = Lists.newArrayList(); EntityPlayer entityplayer; for (int i = 0; i < this.players.size(); ++i) { entityplayer = (EntityPlayer) this.players.get(i); - if (entityplayer.getName().equalsIgnoreCase(gameprofile.getName())) { + if (entityplayer.getUniqueID().equals(uuid)) { arraylist.add(entityplayer); } } @@ -395,7 +416,7 @@ public abstract class PlayerList { /* CraftBukkit start Object object; - if (this.server.Q()) { + if (this.server.R()) { object = new DemoPlayerInteractManager(this.server.getWorldServer(0)); } else { object = new PlayerInteractManager(this.server.getWorldServer(0)); @@ -426,7 +447,7 @@ public abstract class PlayerList { entityplayer.dimension = i; Object object; - if (this.server.Q()) { + if (this.server.R()) { object = new DemoPlayerInteractManager(this.server.getWorldServer(entityplayer.dimension)); } else { object = new PlayerInteractManager(this.server.getWorldServer(entityplayer.dimension)); @@ -443,8 +464,8 @@ public abstract class PlayerList { entityplayer1.copyTo(entityplayer, flag); entityplayer1.d(entityplayer.getId()); // WorldServer worldserver = this.server.getWorldServer(entityplayer.dimension); // CraftBukkit - handled later - // this.a(entityplayer1, entityplayer, worldserver); // CraftBukkit - removed + // this.a(entityplayer1, entityplayer, worldserver); // CraftBukkit - removed ChunkCoordinates chunkcoordinates1; // CraftBukkit start - fire PlayerRespawnEvent @@ -750,7 +771,7 @@ public abstract class PlayerList { // worldserver1.s().a(entity, d3, d4, d5, f); if (portal) { Vector velocity = entity.getBukkitEntity().getVelocity(); - worldserver1.getTravelAgent().adjustExit(entity, exit, velocity); // Should be getTravelAgent + worldserver1.getTravelAgent().adjustExit(entity, exit, velocity); entity.setPositionRotation(exit.getX(), exit.getY(), exit.getZ(), exit.getYaw(), exit.getPitch()); if (entity.motX != velocity.getX() || entity.motY != velocity.getY() || entity.motZ != velocity.getZ()) { entity.getBukkitEntity().setVelocity(velocity); @@ -768,8 +789,8 @@ public abstract class PlayerList { } public void tick() { - if (++this.p > 600) { - this.p = 0; + if (++this.t > 600) { + this.t = 0; } /* CraftBukkit start - Remove updating of lag to players -- it spams way to much on big servers. @@ -797,21 +818,25 @@ public abstract class PlayerList { } } - public String c() { + public String b(boolean flag) { String s = ""; + ArrayList arraylist = Lists.newArrayList(this.players); - for (int i = 0; i < this.players.size(); ++i) { + for (int i = 0; i < arraylist.size(); ++i) { if (i > 0) { s = s + ", "; } - s = s + ((EntityPlayer) this.players.get(i)).getName(); + s = s + ((EntityPlayer) arraylist.get(i)).getName(); + if (flag) { + s = s + " (" + ((EntityPlayer) arraylist.get(i)).getUniqueID().toString() + ")"; + } } return s; } - public String[] d() { + public String[] f() { String[] astring = new String[this.players.size()]; for (int i = 0; i < this.players.size(); ++i) { @@ -821,44 +846,53 @@ public abstract class PlayerList { return astring; } - public BanList getNameBans() { - return this.banByName; + public GameProfile[] g() { + GameProfile[] agameprofile = new GameProfile[this.players.size()]; + + for (int i = 0; i < this.players.size(); ++i) { + agameprofile[i] = ((EntityPlayer) this.players.get(i)).getProfile(); + } + + return agameprofile; + } + + public GameProfileBanList getProfileBans() { + return this.j; } - public BanList getIPBans() { - return this.banByIP; + public IpBanList getIPBans() { + return this.k; } - public void addOp(String s) { - this.operators.add(s.toLowerCase()); + public void addOp(GameProfile gameprofile) { + this.operators.add(new OpListEntry(gameprofile, this.server.l())); // CraftBukkit start - Player player = server.server.getPlayerExact(s); + Player player = server.server.getPlayer(gameprofile.getId()); if (player != null) { player.recalculatePermissions(); } // CraftBukkit end } - public void removeOp(String s) { - this.operators.remove(s.toLowerCase()); + public void removeOp(GameProfile gameprofile) { + this.operators.remove(gameprofile); // CraftBukkit start - Player player = server.server.getPlayerExact(s); + Player player = server.server.getPlayer(gameprofile.getId()); if (player != null) { player.recalculatePermissions(); } // CraftBukkit end } - public boolean isWhitelisted(String s) { - s = s.trim().toLowerCase(); - return !this.hasWhitelist || this.operators.contains(s) || this.whitelist.contains(s); + public boolean isWhitelisted(GameProfile gameprofile) { + return !this.hasWhitelist || this.operators.d(gameprofile) || this.whitelist.d(gameprofile); } - public boolean isOp(String s) { + public boolean isOp(GameProfile gameprofile) { // CraftBukkit - fix reference to worldserver array - return this.operators.contains(s.trim().toLowerCase()) || this.server.M() && this.server.worlds.get(0).getWorldData().allowCommands() && this.server.L().equalsIgnoreCase(s) || this.o; + return this.operators.d(gameprofile) || this.server.N() && this.server.worlds.get(0).getWorldData().allowCommands() && this.server.M().equalsIgnoreCase(gameprofile.getName()) || this.s; } public EntityPlayer getPlayer(String s) { @@ -1015,22 +1049,30 @@ public abstract class PlayerList { } } - public void addWhitelist(String s) { - this.whitelist.add(s); + public void addWhitelist(GameProfile gameprofile) { + this.whitelist.add(new WhiteListEntry(gameprofile)); } - public void removeWhitelist(String s) { - this.whitelist.remove(s); + public void removeWhitelist(GameProfile gameprofile) { + this.whitelist.remove(gameprofile); } - public Set getWhitelisted() { + public WhiteList getWhitelist() { return this.whitelist; } - public Set getOPs() { + public String[] getWhitelisted() { + return this.whitelist.getEntries(); + } + + public OpList getOPs() { return this.operators; } + public String[] n() { + return this.operators.getEntries(); + } + public void reloadWhitelist() {} public void b(EntityPlayer entityplayer, WorldServer worldserver) { @@ -1072,7 +1114,7 @@ public abstract class PlayerList { this.hasWhitelist = flag; } - public List h(String s) { + public List b(String s) { ArrayList arraylist = new ArrayList(); Iterator iterator = this.players.iterator(); @@ -1087,29 +1129,29 @@ public abstract class PlayerList { return arraylist; } - public int o() { - return this.m; + public int s() { + return this.q; } public MinecraftServer getServer() { return this.server; } - public NBTTagCompound q() { + public NBTTagCompound t() { return null; } private void a(EntityPlayer entityplayer, EntityPlayer entityplayer1, World world) { if (entityplayer1 != null) { entityplayer.playerInteractManager.setGameMode(entityplayer1.playerInteractManager.getGameMode()); - } else if (this.n != null) { - entityplayer.playerInteractManager.setGameMode(this.n); + } else if (this.r != null) { + entityplayer.playerInteractManager.setGameMode(this.r); } entityplayer.playerInteractManager.b(world.getWorldData().getGameType()); } - public void r() { + public void u() { for (int i = 0; i < this.players.size(); ++i) { ((EntityPlayer) this.players.get(i)).playerConnection.disconnect(this.server.server.getShutdownMessage()); // CraftBukkit - add custom shutdown message } @@ -1132,20 +1174,32 @@ public abstract class PlayerList { this.sendMessage(ichatbasecomponent, true); } - public ServerStatisticManager i(String s) { - ServerStatisticManager serverstatisticmanager = (ServerStatisticManager) this.j.get(s); + public ServerStatisticManager a(EntityHuman entityhuman) { + UUID uuid = entityhuman.getUniqueID(); + ServerStatisticManager serverstatisticmanager = uuid == null ? null : (ServerStatisticManager) this.n.get(uuid); if (serverstatisticmanager == null) { - serverstatisticmanager = new ServerStatisticManager(this.server, new File(this.server.getWorldServer(0).getDataManager().getDirectory(), "stats/" + s + ".json")); + File file1 = new File(this.server.getWorldServer(0).getDataManager().getDirectory(), "stats"); + File file2 = new File(file1, uuid.toString() + ".json"); + + if (!file2.exists()) { + File file3 = new File(file1, entityhuman.getName() + ".json"); + + if (file3.exists() && file3.isFile()) { + file3.renameTo(file2); + } + } + + serverstatisticmanager = new ServerStatisticManager(this.server, file2); serverstatisticmanager.a(); - this.j.put(s, serverstatisticmanager); + this.n.put(uuid, serverstatisticmanager); } return serverstatisticmanager; } public void a(int i) { - this.m = i; + this.q = i; if (this.server.worldServer != null) { WorldServer[] aworldserver = this.server.worldServer; int j = aworldserver.length; diff --git a/src/main/java/net/minecraft/server/RegionFile.java b/src/main/java/net/minecraft/server/RegionFile.java index e9cb09f9..9cd34a44 100644 --- a/src/main/java/net/minecraft/server/RegionFile.java +++ b/src/main/java/net/minecraft/server/RegionFile.java @@ -244,7 +244,7 @@ public class RegionFile { } } - this.b(i, j, (int) (MinecraftServer.aq() / 1000L)); + this.b(i, j, (int) (MinecraftServer.ar() / 1000L)); } catch (IOException ioexception) { ioexception.printStackTrace(); } diff --git a/src/main/java/net/minecraft/server/ThreadCommandReader.java b/src/main/java/net/minecraft/server/ThreadCommandReader.java index 0e24bd7d..a5e8a45e 100644 --- a/src/main/java/net/minecraft/server/ThreadCommandReader.java +++ b/src/main/java/net/minecraft/server/ThreadCommandReader.java @@ -39,7 +39,7 @@ class ThreadCommandReader extends Thread { // CraftBukkit end } } catch (IOException ioexception) { - DedicatedServer.aA().error("Exception handling console input", ioexception); + DedicatedServer.aF().error("Exception handling console input", ioexception); } } } diff --git a/src/main/java/net/minecraft/server/ThreadPlayerLookupUUID.java b/src/main/java/net/minecraft/server/ThreadPlayerLookupUUID.java index 496b7c98..6b91be70 100644 --- a/src/main/java/net/minecraft/server/ThreadPlayerLookupUUID.java +++ b/src/main/java/net/minecraft/server/ThreadPlayerLookupUUID.java @@ -1,6 +1,7 @@ package net.minecraft.server; import java.math.BigInteger; +import java.util.UUID; import net.minecraft.util.com.mojang.authlib.GameProfile; import net.minecraft.util.com.mojang.authlib.exceptions.AuthenticationUnavailableException; @@ -21,20 +22,22 @@ class ThreadPlayerLookupUUID extends Thread { } public void run() { + GameProfile gameprofile = LoginListener.a(this.a); + try { - String s = (new BigInteger(MinecraftEncryption.a(LoginListener.a(this.a), LoginListener.b(this.a).J().getPublic(), LoginListener.c(this.a)))).toString(16); + String s = (new BigInteger(MinecraftEncryption.a(LoginListener.b(this.a), LoginListener.c(this.a).K().getPublic(), LoginListener.d(this.a)))).toString(16); - LoginListener.a(this.a, LoginListener.b(this.a).at().hasJoinedServer(new GameProfile((String) null, LoginListener.d(this.a).getName()), s)); - if (LoginListener.d(this.a) != null) { + LoginListener.a(this.a, LoginListener.c(this.a).av().hasJoinedServer(new GameProfile((UUID) null, gameprofile.getName()), s)); + if (LoginListener.a(this.a) != null) { // CraftBukkit start - fire PlayerPreLoginEvent if (!this.a.networkManager.isConnected()) { return; } - String playerName = LoginListener.d(this.a).getName(); + String playerName = LoginListener.a(this.a).getName(); java.net.InetAddress address = ((java.net.InetSocketAddress) a.networkManager.getSocketAddress()).getAddress(); - java.util.UUID uniqueId = UtilUUID.b(LoginListener.d(this.a).getId()); - final org.bukkit.craftbukkit.CraftServer server = LoginListener.b(this.a).server; + java.util.UUID uniqueId = LoginListener.a(this.a).getId(); + final org.bukkit.craftbukkit.CraftServer server = LoginListener.c(this.a).server; AsyncPlayerPreLoginEvent asyncEvent = new AsyncPlayerPreLoginEvent(playerName, address, uniqueId); server.getPluginManager().callEvent(asyncEvent); @@ -51,7 +54,7 @@ class ThreadPlayerLookupUUID extends Thread { return event.getResult(); }}; - LoginListener.b(this.a).processQueue.add(waitable); + LoginListener.c(this.a).processQueue.add(waitable); if (waitable.get() != PlayerPreLoginEvent.Result.ALLOWED) { this.a.disconnect(event.getKickMessage()); return; @@ -64,19 +67,29 @@ class ThreadPlayerLookupUUID extends Thread { } // CraftBukkit end - LoginListener.e().info("UUID of player " + LoginListener.d(this.a).getName() + " is " + LoginListener.d(this.a).getId()); + LoginListener.e().info("UUID of player " + LoginListener.a(this.a).getName() + " is " + LoginListener.a(this.a).getId()); + LoginListener.a(this.a, EnumProtocolState.READY_TO_ACCEPT); + } else if (LoginListener.c(this.a).N()) { + LoginListener.e().warn("Failed to verify username but will let them in anyway!"); + LoginListener.a(this.a, this.a.a(gameprofile)); LoginListener.a(this.a, EnumProtocolState.READY_TO_ACCEPT); } else { this.a.disconnect("Failed to verify username!"); - LoginListener.e().error("Username \'" + LoginListener.d(this.a).getName() + "\' tried to join with an invalid session"); + LoginListener.e().error("Username \'" + LoginListener.a(this.a).getName() + "\' tried to join with an invalid session"); } } catch (AuthenticationUnavailableException authenticationunavailableexception) { - this.a.disconnect("Authentication servers are down. Please try again later, sorry!"); - LoginListener.e().error("Couldn\'t verify username because servers are unavailable"); + if (LoginListener.c(this.a).N()) { + LoginListener.e().warn("Authentication servers are down but will let them in anyway!"); + LoginListener.a(this.a, this.a.a(gameprofile)); + LoginListener.a(this.a, EnumProtocolState.READY_TO_ACCEPT); + } else { + this.a.disconnect("Authentication servers are down. Please try again later, sorry!"); + LoginListener.e().error("Couldn\'t verify username because servers are unavailable"); + } // CraftBukkit start - catch all exceptions } catch (Exception exception) { this.a.disconnect("Failed to verify username!"); - LoginListener.b(this.a).server.getLogger().log(java.util.logging.Level.WARNING, "Exception verifying " + LoginListener.d(this.a).getName(), exception); + LoginListener.c(this.a).server.getLogger().log(java.util.logging.Level.WARNING, "Exception verifying " + LoginListener.a(this.a).getName(), exception); // CraftBukkit end } } diff --git a/src/main/java/net/minecraft/server/TileEntitySkull.java b/src/main/java/net/minecraft/server/TileEntitySkull.java index b241cfee..748f00a6 100644 --- a/src/main/java/net/minecraft/server/TileEntitySkull.java +++ b/src/main/java/net/minecraft/server/TileEntitySkull.java @@ -1,10 +1,16 @@ package net.minecraft.server; +import java.util.UUID; + +import net.minecraft.util.com.google.common.collect.Iterables; +import net.minecraft.util.com.mojang.authlib.GameProfile; +import net.minecraft.util.com.mojang.authlib.properties.Property; + public class TileEntitySkull extends TileEntity { private int a; private int i; - private String j = ""; + private GameProfile j = null; public TileEntitySkull() {} @@ -12,18 +18,32 @@ public class TileEntitySkull extends TileEntity { super.b(nbttagcompound); nbttagcompound.setByte("SkullType", (byte) (this.a & 255)); nbttagcompound.setByte("Rot", (byte) (this.i & 255)); - nbttagcompound.setString("ExtraType", this.j); + if (this.j != null) { + NBTTagCompound nbttagcompound1 = new NBTTagCompound(); + + GameProfileSerializer.a(nbttagcompound1, this.j); + nbttagcompound.set("Owner", nbttagcompound1); + } } public void a(NBTTagCompound nbttagcompound) { super.a(nbttagcompound); this.a = nbttagcompound.getByte("SkullType"); this.i = nbttagcompound.getByte("Rot"); - if (nbttagcompound.hasKeyOfType("ExtraType", 8)) { - this.j = nbttagcompound.getString("ExtraType"); + if (this.a == 3) { + if (nbttagcompound.hasKeyOfType("Owner", 10)) { + this.j = GameProfileSerializer.a(nbttagcompound.getCompound("Owner")); + } else if (nbttagcompound.hasKeyOfType("ExtraType", 8) && !UtilColor.b(nbttagcompound.getString("ExtraType"))) { + this.j = new GameProfile((UUID) null, nbttagcompound.getString("ExtraType")); + this.d(); + } } } + public GameProfile getGameProfile() { + return this.j; + } + public Packet getUpdatePacket() { NBTTagCompound nbttagcompound = new NBTTagCompound(); @@ -31,9 +51,34 @@ public class TileEntitySkull extends TileEntity { return new PacketPlayOutTileEntityData(this.x, this.y, this.z, 4, nbttagcompound); } - public void setSkullType(int i, String s) { + public void setSkullType(int i) { this.a = i; - this.j = s; + this.j = null; + } + + public void setGameProfile(GameProfile gameprofile) { + this.a = 3; + this.j = gameprofile; + this.d(); + } + + private void d() { + if (this.j != null && !UtilColor.b(this.j.getName())) { + if (!this.j.isComplete() || !this.j.getProperties().containsKey("textures")) { + GameProfile gameprofile = MinecraftServer.getServer().getUserCache().a(this.j.getName()); + + if (gameprofile != null) { + Property property = (Property) Iterables.getFirst(gameprofile.getProperties().get("textures"), null); + + if (property == null) { + gameprofile = MinecraftServer.getServer().av().fillProfileProperties(gameprofile, true); + } + + this.j = gameprofile; + this.update(); + } + } + } } public int getSkullType() { @@ -49,8 +94,4 @@ public class TileEntitySkull extends TileEntity { return this.i; } // CraftBukkit end - - public String getExtraType() { - return this.j; - } } diff --git a/src/main/java/net/minecraft/server/World.java b/src/main/java/net/minecraft/server/World.java index 2f514b5e..0f97f78a 100644 --- a/src/main/java/net/minecraft/server/World.java +++ b/src/main/java/net/minecraft/server/World.java @@ -8,6 +8,7 @@ import java.util.Iterator; import java.util.List; import java.util.Random; import java.util.Set; +import java.util.UUID; import java.util.concurrent.Callable; // CraftBukkit start @@ -2532,8 +2533,22 @@ public abstract class World implements IBlockAccess { public EntityHuman a(String s) { for (int i = 0; i < this.players.size(); ++i) { - if (s.equals(((EntityHuman) this.players.get(i)).getName())) { - return (EntityHuman) this.players.get(i); + EntityHuman entityhuman = (EntityHuman) this.players.get(i); + + if (s.equals(entityhuman.getName())) { + return entityhuman; + } + } + + return null; + } + + public EntityHuman a(UUID uuid) { + for (int i = 0; i < this.players.size(); ++i) { + EntityHuman entityhuman = (EntityHuman) this.players.get(i); + + if (uuid.equals(entityhuman.getUniqueID())) { + return entityhuman; } } @@ -2726,7 +2741,7 @@ public abstract class World implements IBlockAccess { public Calendar V() { if (this.getTime() % 600L == 0L) { - this.J.setTimeInMillis(MinecraftServer.aq()); + this.J.setTimeInMillis(MinecraftServer.ar()); } return this.J; diff --git a/src/main/java/net/minecraft/server/WorldNBTStorage.java b/src/main/java/net/minecraft/server/WorldNBTStorage.java index f0666a36..fabc72ba 100644 --- a/src/main/java/net/minecraft/server/WorldNBTStorage.java +++ b/src/main/java/net/minecraft/server/WorldNBTStorage.java @@ -24,14 +24,14 @@ public class WorldNBTStorage implements IDataManager, IPlayerFileData { private final File baseDir; private final File playerDir; private final File dataDir; - private final long sessionId = MinecraftServer.aq(); + private final long sessionId = MinecraftServer.ar(); private final String f; private UUID uuid = null; // CraftBukkit public WorldNBTStorage(File file1, String s, boolean flag) { this.baseDir = new File(file1, s); this.baseDir.mkdirs(); - this.playerDir = new File(this.baseDir, "players"); + this.playerDir = new File(this.baseDir, "playerdata"); this.dataDir = new File(this.baseDir, "data"); this.dataDir.mkdirs(); this.f = s; @@ -177,8 +177,8 @@ public class WorldNBTStorage implements IDataManager, IPlayerFileData { NBTTagCompound nbttagcompound = new NBTTagCompound(); entityhuman.e(nbttagcompound); - File file1 = new File(this.playerDir, entityhuman.getName() + ".dat.tmp"); - File file2 = new File(this.playerDir, entityhuman.getName() + ".dat"); + File file1 = new File(this.playerDir, entityhuman.getUniqueID().toString() + ".dat.tmp"); + File file2 = new File(this.playerDir, entityhuman.getUniqueID().toString() + ".dat"); NBTCompressedStreamTools.a(nbttagcompound, (OutputStream) (new FileOutputStream(file1))); if (file2.exists()) { @@ -192,7 +192,17 @@ public class WorldNBTStorage implements IDataManager, IPlayerFileData { } public NBTTagCompound load(EntityHuman entityhuman) { - NBTTagCompound nbttagcompound = this.getPlayerData(entityhuman.getName()); + NBTTagCompound nbttagcompound = null; + + try { + File file1 = new File(this.playerDir, entityhuman.getUniqueID().toString() + ".dat"); + + if (file1.exists() && file1.isFile()) { + nbttagcompound = NBTCompressedStreamTools.a((InputStream) (new FileInputStream(file1))); + } + } catch (Exception exception) { + a.warn("Failed to load player data for " + entityhuman.getName()); + } if (nbttagcompound != null) { // CraftBukkit start @@ -201,6 +211,7 @@ public class WorldNBTStorage implements IDataManager, IPlayerFileData { player.setFirstPlayed(new File(playerDir, entityhuman.getName() + ".dat").lastModified()); } // CraftBukkit end + entityhuman.f(nbttagcompound); } diff --git a/src/main/java/net/minecraft/server/WorldServer.java b/src/main/java/net/minecraft/server/WorldServer.java index 29fb40d2..843761a5 100644 --- a/src/main/java/net/minecraft/server/WorldServer.java +++ b/src/main/java/net/minecraft/server/WorldServer.java @@ -9,6 +9,7 @@ import java.util.Random; import java.util.Set; import java.util.TreeSet; +import net.minecraft.util.com.google.common.collect.Lists; import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.Logger; @@ -765,14 +766,14 @@ public class WorldServer extends World implements org.bukkit.BlockChangeDelegate } this.chunkProvider.saveChunks(flag, iprogressupdate); - // CraftBukkit - List -> Collection - Collection list = this.chunkProviderServer.a(); - Iterator iterator = list.iterator(); + // CraftBukkit - ArrayList -> Collection + Collection arraylist = this.chunkProviderServer.a(); + Iterator iterator = arraylist.iterator(); while (iterator.hasNext()) { Chunk chunk = (Chunk) iterator.next(); - if (!this.manager.a(chunk.locX, chunk.locZ)) { + if (chunk != null && !this.manager.a(chunk.locX, chunk.locZ)) { this.chunkProviderServer.queueUnload(chunk.locX, chunk.locZ); } } @@ -787,7 +788,7 @@ public class WorldServer extends World implements org.bukkit.BlockChangeDelegate protected void a() throws ExceptionWorldConflict { // CraftBukkit - added throws this.G(); - this.dataManager.saveWorldData(this.worldData, this.server.getPlayerList().q()); + this.dataManager.saveWorldData(this.worldData, this.server.getPlayerList().t()); // CraftBukkit start - save worldMaps once, rather than once per shared world if (!(this instanceof SecondaryWorldServer)) { this.worldMaps.a(); @@ -961,7 +962,7 @@ public class WorldServer extends World implements org.bukkit.BlockChangeDelegate } protected int p() { - return this.server.getPlayerList().o(); + return this.server.getPlayerList().s(); } public MinecraftServer getMinecraftServer() { diff --git a/src/main/java/org/bukkit/craftbukkit/CraftBanEntry.java b/src/main/java/org/bukkit/craftbukkit/CraftIpBanEntry.java index 39ece748..583f9ab6 100644 --- a/src/main/java/org/bukkit/craftbukkit/CraftBanEntry.java +++ b/src/main/java/org/bukkit/craftbukkit/CraftIpBanEntry.java @@ -1,21 +1,21 @@ package org.bukkit.craftbukkit; -import java.util.Date; +import net.minecraft.server.IpBanEntry; +import net.minecraft.server.IpBanList; -import net.minecraft.server.BanEntry; -import net.minecraft.server.BanList; +import java.util.Date; -public final class CraftBanEntry implements org.bukkit.BanEntry { - private final BanList list; - private final String name; +public final class CraftIpBanEntry implements org.bukkit.BanEntry { + private final IpBanList list; + private final String target; private Date created; private String source; private Date expiration; private String reason; - public CraftBanEntry(BanEntry entry, BanList list) { + public CraftIpBanEntry(String target, IpBanEntry entry, IpBanList list) { this.list = list; - this.name = entry.getName(); + this.target = target; this.created = entry.getCreated() != null ? new Date(entry.getCreated().getTime()) : null; this.source = entry.getSource(); this.expiration = entry.getExpires() != null ? new Date(entry.getExpires().getTime()) : null; @@ -24,7 +24,7 @@ public final class CraftBanEntry implements org.bukkit.BanEntry { @Override public String getTarget() { - return this.name; + return this.target; } @Override @@ -73,14 +73,8 @@ public final class CraftBanEntry implements org.bukkit.BanEntry { @Override public void save() { - BanEntry entry = new BanEntry(this.name); - entry.setCreated(this.created); - entry.setSource(this.source); - entry.setExpires(this.expiration); - entry.setReason(this.reason); - + IpBanEntry entry = new IpBanEntry(target, this.created, this.source, this.expiration, this.reason); this.list.add(entry); this.list.save(); } - } diff --git a/src/main/java/org/bukkit/craftbukkit/CraftBanList.java b/src/main/java/org/bukkit/craftbukkit/CraftIpBanList.java index e4abd053..75dc31bb 100644 --- a/src/main/java/org/bukkit/craftbukkit/CraftBanList.java +++ b/src/main/java/org/bukkit/craftbukkit/CraftIpBanList.java @@ -1,21 +1,20 @@ package org.bukkit.craftbukkit; -import java.util.Collection; +import java.net.InetSocketAddress; import java.util.Date; import java.util.Set; +import net.minecraft.server.IpBanEntry; +import net.minecraft.server.IpBanList; import org.apache.commons.lang.StringUtils; import org.apache.commons.lang.Validate; import com.google.common.collect.ImmutableSet; -import net.minecraft.server.BanEntry; -import net.minecraft.server.BanList; +public class CraftIpBanList implements org.bukkit.BanList { + private final IpBanList list; -public class CraftBanList implements org.bukkit.BanList { - private final BanList list; - - public CraftBanList(BanList list){ + public CraftIpBanList(IpBanList list) { this.list = list; } @@ -23,33 +22,34 @@ public class CraftBanList implements org.bukkit.BanList { public org.bukkit.BanEntry getBanEntry(String target) { Validate.notNull(target, "Target cannot be null"); - if (!list.getEntries().containsKey(target)) { + IpBanEntry entry = (IpBanEntry) list.get(target); + if (entry == null) { return null; } - return new CraftBanEntry((BanEntry) list.getEntries().get(target), list); + return new CraftIpBanEntry(target, entry, list); } @Override public org.bukkit.BanEntry addBan(String target, String reason, Date expires, String source) { Validate.notNull(target, "Ban target cannot be null"); - BanEntry entry = new BanEntry(target); - entry.setSource(StringUtils.isBlank(source) ? entry.getSource() : source); // Use default if null/empty - entry.setExpires(expires); // Null values are interpreted as "forever" - entry.setReason(StringUtils.isBlank(reason) ? entry.getReason() : reason); // Use default if null/empty + IpBanEntry entry = new IpBanEntry(target, new Date(), + StringUtils.isBlank(source) ? null : source, expires, + StringUtils.isBlank(reason) ? null : reason); list.add(entry); list.save(); - return new CraftBanEntry(entry, list); + return new CraftIpBanEntry(target, entry, list); } @Override public Set<org.bukkit.BanEntry> getBanEntries() { ImmutableSet.Builder<org.bukkit.BanEntry> builder = ImmutableSet.builder(); - for (BanEntry entry : (Collection<BanEntry>) list.getEntries().values()) { - builder.add(new CraftBanEntry(entry, list)); + for (String target : list.getEntries()) { + builder.add(new CraftIpBanEntry(target, (IpBanEntry) list.get(target), list)); } + return builder.build(); } @@ -57,7 +57,7 @@ public class CraftBanList implements org.bukkit.BanList { public boolean isBanned(String target) { Validate.notNull(target, "Target cannot be null"); - return list.isBanned(target); + return list.isBanned(InetSocketAddress.createUnresolved(target, 0)); } @Override @@ -66,5 +66,4 @@ public class CraftBanList implements org.bukkit.BanList { list.remove(target); } - } diff --git a/src/main/java/org/bukkit/craftbukkit/CraftOfflinePlayer.java b/src/main/java/org/bukkit/craftbukkit/CraftOfflinePlayer.java index 24b00662..bec41346 100644 --- a/src/main/java/org/bukkit/craftbukkit/CraftOfflinePlayer.java +++ b/src/main/java/org/bukkit/craftbukkit/CraftOfflinePlayer.java @@ -6,11 +6,11 @@ import java.util.List; import java.util.Map; import java.util.UUID; -import net.minecraft.server.BanEntry; import net.minecraft.server.EntityPlayer; import net.minecraft.server.NBTTagCompound; import net.minecraft.server.WorldNBTStorage; +import net.minecraft.util.com.mojang.authlib.GameProfile; import org.bukkit.BanList; import org.bukkit.Bukkit; import org.bukkit.Location; @@ -24,14 +24,19 @@ import org.bukkit.plugin.Plugin; @SerializableAs("Player") public class CraftOfflinePlayer implements OfflinePlayer, ConfigurationSerializable { - private final String name; + private final GameProfile profile; private final CraftServer server; private final WorldNBTStorage storage; - protected CraftOfflinePlayer(CraftServer server, String name) { + protected CraftOfflinePlayer(CraftServer server, GameProfile profile) { this.server = server; - this.name = name; + this.profile = profile; this.storage = (WorldNBTStorage) (server.console.worlds.get(0).getDataManager()); + + } + + public GameProfile getProfile() { + return profile; } public boolean isOnline() { @@ -39,86 +44,96 @@ public class CraftOfflinePlayer implements OfflinePlayer, ConfigurationSerializa } public String getName() { - return name; - } - - // TODO: In 1.7.6+ OfflinePlayer lookup should be by UUID and store it like it does the name now - public UUID getUniqueId() { - NBTTagCompound data = getData(); - if (data == null) { - return null; + Player player = getPlayer(); + if (player != null) { + return player.getName(); } - if (data.hasKeyOfType("UUIDMost", 4) && data.hasKeyOfType("UUIDLeast", 4)) { - return new UUID(data.getLong("UUIDMost"), data.getLong("UUIDLeast")); + NBTTagCompound data = getBukkitData(); + + if (data != null) { + if (data.hasKey("lastKnownName")) { + return data.getString("lastKnownName"); + } } return null; } + public UUID getUniqueId() { + return profile.getId(); + } + public Server getServer() { return server; } public boolean isOp() { - return server.getHandle().isOp(getName().toLowerCase()); + return server.getHandle().isOp(profile); } public void setOp(boolean value) { - if (value == isOp()) return; + if (value == isOp()) { + return; + } if (value) { - server.getHandle().addOp(getName().toLowerCase()); + server.getHandle().addOp(profile); } else { - server.getHandle().removeOp(getName().toLowerCase()); + server.getHandle().removeOp(profile); } } public boolean isBanned() { - return server.getBanList(BanList.Type.NAME).isBanned(getName()); + return server.getBanList(BanList.Type.UUID).isBanned(getUniqueId().toString()); } public void setBanned(boolean value) { if (value) { - server.getBanList(BanList.Type.NAME).addBan(getName(), null, null, null); + server.getBanList(BanList.Type.UUID).addBan(getUniqueId().toString(), null, null, null); } else { - server.getBanList(BanList.Type.NAME).pardon(getName()); + server.getBanList(BanList.Type.UUID).pardon(getUniqueId().toString()); } } public boolean isWhitelisted() { - return server.getHandle().getWhitelisted().contains(name.toLowerCase()); + return server.getHandle().isWhitelisted(profile); } public void setWhitelisted(boolean value) { if (value) { - server.getHandle().addWhitelist(name.toLowerCase()); + server.getHandle().addWhitelist(profile); } else { - server.getHandle().removeWhitelist(name.toLowerCase()); + server.getHandle().removeWhitelist(profile); } } public Map<String, Object> serialize() { Map<String, Object> result = new LinkedHashMap<String, Object>(); - result.put("name", name); + result.put("UUID", profile.getId().toString()); return result; } public static OfflinePlayer deserialize(Map<String, Object> args) { - return Bukkit.getServer().getOfflinePlayer((String) args.get("name")); + // Backwards comparability + if (args.get("name") != null) { + return Bukkit.getServer().getOfflinePlayer((String) args.get("name")); + } + + return Bukkit.getServer().getOfflinePlayer(UUID.fromString((String) args.get("UUID"))); } @Override public String toString() { - return getClass().getSimpleName() + "[name=" + name + "]"; + return getClass().getSimpleName() + "[UUID=" + profile.getId() + "]"; } public Player getPlayer() { for (Object obj : server.getHandle().players) { EntityPlayer player = (EntityPlayer) obj; - if (player.getName().equalsIgnoreCase(getName())) { + if (player.getUniqueID().equals(getUniqueId())) { return (player.playerConnection != null) ? player.playerConnection.getPlayer() : null; } } @@ -128,28 +143,27 @@ public class CraftOfflinePlayer implements OfflinePlayer, ConfigurationSerializa @Override public boolean equals(Object obj) { - if (obj == null) { - return false; - } - if (!(obj instanceof OfflinePlayer)) { + if (obj == null || !(obj instanceof OfflinePlayer)) { return false; } + OfflinePlayer other = (OfflinePlayer) obj; - if ((this.getName() == null) || (other.getName() == null)) { + if ((this.getUniqueId() == null) || (other.getUniqueId() == null)) { return false; } - return this.getName().equalsIgnoreCase(other.getName()); + + return this.getUniqueId().equals(other.getUniqueId()); } @Override public int hashCode() { int hash = 5; - hash = 97 * hash + (this.getName() != null ? this.getName().toLowerCase().hashCode() : 0); + hash = 97 * hash + (this.getUniqueId() != null ? this.getUniqueId().toString().hashCode() : 0); return hash; } private NBTTagCompound getData() { - return storage.getPlayerData(getName()); + return storage.getPlayerData(getUniqueId().toString()); } private NBTTagCompound getBukkitData() { @@ -166,7 +180,7 @@ public class CraftOfflinePlayer implements OfflinePlayer, ConfigurationSerializa } private File getDataFile() { - return new File(storage.getPlayerDir(), name + ".dat"); + return new File(storage.getPlayerDir(), getUniqueId() + ".dat"); } public long getFirstPlayed() { diff --git a/src/main/java/org/bukkit/craftbukkit/CraftProfileBanEntry.java b/src/main/java/org/bukkit/craftbukkit/CraftProfileBanEntry.java new file mode 100644 index 00000000..499c5aac --- /dev/null +++ b/src/main/java/org/bukkit/craftbukkit/CraftProfileBanEntry.java @@ -0,0 +1,81 @@ +package org.bukkit.craftbukkit; + +import net.minecraft.server.GameProfileBanEntry; +import net.minecraft.server.GameProfileBanList; +import net.minecraft.util.com.mojang.authlib.GameProfile; + +import java.util.Date; + +public final class CraftProfileBanEntry implements org.bukkit.BanEntry { + private final GameProfileBanList list; + private final GameProfile profile; + private Date created; + private String source; + private Date expiration; + private String reason; + + public CraftProfileBanEntry(GameProfile profile, GameProfileBanEntry entry, GameProfileBanList list) { + this.list = list; + this.profile = profile; + this.created = entry.getCreated() != null ? new Date(entry.getCreated().getTime()) : null; + this.source = entry.getSource(); + this.expiration = entry.getExpires() != null ? new Date(entry.getExpires().getTime()) : null; + this.reason = entry.getReason(); + } + + @Override + public String getTarget() { + return this.profile.getId().toString(); + } + + @Override + public Date getCreated() { + return this.created == null ? null : (Date) this.created.clone(); + } + + @Override + public void setCreated(Date created) { + this.created = created; + } + + @Override + public String getSource() { + return this.source; + } + + @Override + public void setSource(String source) { + this.source = source; + } + + @Override + public Date getExpiration() { + return this.expiration == null ? null : (Date) this.expiration.clone(); + } + + @Override + public void setExpiration(Date expiration) { + if (expiration != null && expiration.getTime() == new Date(0, 0, 0, 0, 0, 0).getTime()) { + expiration = null; // Forces "forever" + } + + this.expiration = expiration; + } + + @Override + public String getReason() { + return this.reason; + } + + @Override + public void setReason(String reason) { + this.reason = reason; + } + + @Override + public void save() { + GameProfileBanEntry entry = new GameProfileBanEntry(profile, this.created, this.source, this.expiration, this.reason); + this.list.add(entry); + this.list.save(); + } +} diff --git a/src/main/java/org/bukkit/craftbukkit/CraftProfileBanList.java b/src/main/java/org/bukkit/craftbukkit/CraftProfileBanList.java new file mode 100644 index 00000000..c077daa1 --- /dev/null +++ b/src/main/java/org/bukkit/craftbukkit/CraftProfileBanList.java @@ -0,0 +1,86 @@ +package org.bukkit.craftbukkit; + +import java.util.Date; +import java.util.Set; +import java.util.UUID; + +import net.minecraft.server.GameProfileBanEntry; +import net.minecraft.server.GameProfileBanList; +import net.minecraft.util.com.mojang.authlib.GameProfile; + +import org.apache.commons.lang.StringUtils; +import org.apache.commons.lang.Validate; + +import com.google.common.collect.ImmutableSet; + +public class CraftProfileBanList implements org.bukkit.BanList { + private final GameProfileBanList list; + + public CraftProfileBanList(GameProfileBanList list){ + this.list = list; + } + + @Override + public org.bukkit.BanEntry getBanEntry(String target) { + Validate.notNull(target, "Target cannot be null"); + + UUID id = UUID.fromString(target); + GameProfile profile = new GameProfile(id, null); + + GameProfileBanEntry entry = (GameProfileBanEntry) list.get(profile); + if (entry == null) { + return null; + } + + return new CraftProfileBanEntry(profile, entry, list); + } + + @Override + public org.bukkit.BanEntry addBan(String target, String reason, Date expires, String source) { + Validate.notNull(target, "Ban target cannot be null"); + + UUID id = UUID.fromString(target); + GameProfile profile = new GameProfile(id, null); + + GameProfileBanEntry entry = new GameProfileBanEntry(profile, new Date(), + StringUtils.isBlank(source) ? null : source, expires, + StringUtils.isBlank(reason) ? null : reason); + + list.add(entry); + list.save(); + return new CraftProfileBanEntry(profile, entry, list); + } + + @Override + public Set<org.bukkit.BanEntry> getBanEntries() { + ImmutableSet.Builder<org.bukkit.BanEntry> builder = ImmutableSet.builder(); + for (String target : list.getEntries()) { + UUID id = UUID.fromString(target); + GameProfile profile = new GameProfile(id, null); + + builder.add(new CraftProfileBanEntry(profile, (GameProfileBanEntry) list.get(profile), list)); + } + + return builder.build(); + } + + @Override + public boolean isBanned(String target) { + Validate.notNull(target, "Target cannot be null"); + + UUID id = UUID.fromString(target); + GameProfile profile = new GameProfile(id, null); + + return list.isBanned(profile); + } + + @Override + public void pardon(String target) { + Validate.notNull(target, "Target cannot be null"); + + UUID id = UUID.fromString(target); + GameProfile profile = new GameProfile(id, null); + + list.remove(profile); + } +} diff --git a/src/main/java/org/bukkit/craftbukkit/CraftServer.java b/src/main/java/org/bukkit/craftbukkit/CraftServer.java index 2b5aa31a..748d887d 100644 --- a/src/main/java/org/bukkit/craftbukkit/CraftServer.java +++ b/src/main/java/org/bukkit/craftbukkit/CraftServer.java @@ -15,7 +15,6 @@ import java.util.LinkedHashSet; import java.util.List; import java.util.Map; import java.util.Set; -import java.util.UUID; import java.util.logging.Level; import java.util.logging.Logger; @@ -92,6 +91,7 @@ import net.minecraft.server.WorldServer; import net.minecraft.server.WorldSettings; import net.minecraft.server.WorldType; import net.minecraft.util.com.google.common.base.Charsets; +import net.minecraft.util.com.mojang.authlib.GameProfile; import net.minecraft.util.io.netty.buffer.ByteBuf; import net.minecraft.util.io.netty.buffer.ByteBufOutputStream; import net.minecraft.util.io.netty.buffer.Unpooled; @@ -204,7 +204,7 @@ public final class CraftServer implements Server { private YamlConfiguration configuration; private YamlConfiguration commandsConfiguration; private final Yaml yaml = new Yaml(new SafeConstructor()); - private final Map<String, OfflinePlayer> offlinePlayers = new MapMaker().softValues().makeMap(); + private final Map<java.util.UUID, OfflinePlayer> offlinePlayers = new MapMaker().softValues().makeMap(); private final AutoUpdater updater; private final EntityMetadataStore entityMetadata = new EntityMetadataStore(); private final PlayerMetadataStore playerMetadata = new PlayerMetadataStore(); @@ -514,7 +514,7 @@ public final class CraftServer implements Server { } // TODO: In 1.7.6+ this should use the server's UUID->EntityPlayer map - public Player getPlayer(UUID id) { + public Player getPlayer(java.util.UUID id) { for (Player player : getOnlinePlayers()) { if (player.getUniqueId().equals(id)) { return player; @@ -734,7 +734,7 @@ public final class CraftServer implements Server { loadIcon(); playerList.getIPBans().load(); - playerList.getNameBans().load(); + playerList.getProfileBans().load(); for (WorldServer world : console.worlds) { world.difficulty = difficulty; @@ -1013,7 +1013,7 @@ public final class CraftServer implements Server { return worlds.get(name.toLowerCase()); } - public World getWorld(UUID uid) { + public World getWorld(java.util.UUID uid) { for (World world : worlds.values()) { if (world.getUID().equals(uid)) { return world; @@ -1258,54 +1258,44 @@ public final class CraftServer implements Server { } public OfflinePlayer getOfflinePlayer(String name) { - return getOfflinePlayer(name, true); - } - - public OfflinePlayer getOfflinePlayer(String name, boolean search) { Validate.notNull(name, "Name cannot be null"); - OfflinePlayer result = getPlayerExact(name); - String lname = name.toLowerCase(); + // This is potentially blocking :( + GameProfile profile = MinecraftServer.getServer().getUserCache().a(name); + if (profile == null) { + // Make an OfflinePlayer using an offline mode UUID since the name has no profile + return getOfflinePlayer(new GameProfile(java.util.UUID.nameUUIDFromBytes(("OfflinePlayer:" + name).getBytes(Charsets.UTF_8)), name)); + } - if (result == null) { - result = offlinePlayers.get(lname); + return getOfflinePlayer(profile.getId()); + } - if (result == null) { - if (search) { - WorldNBTStorage storage = (WorldNBTStorage) console.worlds.get(0).getDataManager(); - for (String dat : storage.getPlayerDir().list(new DatFileFilter())) { - String datName = dat.substring(0, dat.length() - 4); - if (datName.equalsIgnoreCase(name)) { - name = datName; - break; - } - } - } + public OfflinePlayer getOfflinePlayer(java.util.UUID id) { + Validate.notNull(id, "UUID cannot be null"); - result = new CraftOfflinePlayer(this, name); - offlinePlayers.put(lname, result); + OfflinePlayer result = getPlayer(id); + if (result == null) { + result = offlinePlayers.get(id); + if (result == null) { + result = new CraftOfflinePlayer(this, new GameProfile(id, null)); + offlinePlayers.put(id, result); } } else { - offlinePlayers.remove(lname); + offlinePlayers.remove(id); } return result; } - // TODO: In 1.7.6+ this should just lookup the UUID-based player data filename - public OfflinePlayer getOfflinePlayer(UUID id) { - String name = MojangNameLookup.lookupName(id); - if (name == null) { - // This is completely wrong - name = "InvalidUUID"; - } - - return getOfflinePlayer(name); + public OfflinePlayer getOfflinePlayer(GameProfile profile) { + OfflinePlayer player = new CraftOfflinePlayer(this, profile); + offlinePlayers.put(profile.getId(), player); + return player; } @SuppressWarnings("unchecked") public Set<String> getIPBans() { - return new HashSet<String>(playerList.getIPBans().getEntries().keySet()); + return new HashSet<String>(Arrays.asList(playerList.getIPBans().getEntries())); } public void banIP(String address) { @@ -1323,28 +1313,34 @@ public final class CraftServer implements Server { public Set<OfflinePlayer> getBannedPlayers() { Set<OfflinePlayer> result = new HashSet<OfflinePlayer>(); - for (Object name : playerList.getNameBans().getEntries().keySet()) { - result.add(getOfflinePlayer((String) name)); + for (String id : playerList.getProfileBans().getEntries()) { + try { + result.add(getOfflinePlayer(java.util.UUID.fromString(id))); + } catch (IllegalArgumentException ex) { + // This shouldn't happen + } } return result; } @Override - public BanList getBanList(BanList.Type type){ + public BanList getBanList(BanList.Type type) { Validate.notNull(type, "Type cannot be null"); switch(type){ case IP: - return new CraftBanList(playerList.getIPBans()); + return new CraftIpBanList(playerList.getIPBans()); case NAME: - default: // Fall through as a player name list for safety - return new CraftBanList(playerList.getNameBans()); + return null; + case UUID: + default: + return new CraftProfileBanList(playerList.getProfileBans()); } } public void setWhitelist(boolean value) { - playerList.hasWhitelist = value; + playerList.setHasWhitelist(value); console.getPropertyManager().a("white-list", value); } @@ -1364,8 +1360,12 @@ public final class CraftServer implements Server { public Set<OfflinePlayer> getOperators() { Set<OfflinePlayer> result = new HashSet<OfflinePlayer>(); - for (Object name : playerList.getOPs()) { - result.add(getOfflinePlayer((String) name)); + for (String id : playerList.getOPs().getEntries()) { + try { + result.add(getOfflinePlayer(java.util.UUID.fromString(id))); + } catch (IllegalArgumentException ex) { + // This shouldn't ever happen + } } return result; @@ -1442,8 +1442,13 @@ public final class CraftServer implements Server { Set<OfflinePlayer> players = new HashSet<OfflinePlayer>(); for (String file : files) { - players.add(getOfflinePlayer(file.substring(0, file.length() - 4), false)); + try { + players.add(getOfflinePlayer(java.util.UUID.fromString(file.substring(0, file.length() - 4)))); + } catch (IllegalArgumentException ex) { + // Who knows what is in this directory, just ignore invalid files + } } + players.addAll(Arrays.asList(getOnlinePlayers())); return players.toArray(new OfflinePlayer[players.size()]); diff --git a/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java b/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java index 5fc334a9..7dded2b4 100644 --- a/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java +++ b/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java @@ -10,6 +10,7 @@ import net.minecraft.server.BlockCocoa; import net.minecraft.server.BlockRedstoneWire; import net.minecraft.server.Blocks; import net.minecraft.server.EnumSkyBlock; +import net.minecraft.server.GameProfileSerializer; import net.minecraft.server.Item; import net.minecraft.server.NBTTagCompound; import net.minecraft.server.TileEntitySkull; @@ -423,9 +424,12 @@ public class CraftBlock implements Block { net.minecraft.server.ItemStack nmsStack = new net.minecraft.server.ItemStack(item, 1, block.getDropData(chunk.getHandle().world, x, y, z)); TileEntitySkull tileentityskull = (TileEntitySkull) chunk.getHandle().world.getTileEntity(x, y, z); - if (tileentityskull.getSkullType() == 3 && tileentityskull.getExtraType() != null && tileentityskull.getExtraType().length() > 0) { + if (tileentityskull.getSkullType() == 3 && tileentityskull.getGameProfile() != null) { nmsStack.setTag(new NBTTagCompound()); - nmsStack.getTag().setString("SkullOwner", tileentityskull.getExtraType()); + NBTTagCompound nbttagcompound = new NBTTagCompound(); + + GameProfileSerializer.a(nbttagcompound, tileentityskull.getGameProfile()); + nmsStack.getTag().set("SkullOwner", nbttagcompound); } drops.add(CraftItemStack.asBukkitCopy(nmsStack)); diff --git a/src/main/java/org/bukkit/craftbukkit/block/CraftSkull.java b/src/main/java/org/bukkit/craftbukkit/block/CraftSkull.java index 4e121a3d..d5447605 100644 --- a/src/main/java/org/bukkit/craftbukkit/block/CraftSkull.java +++ b/src/main/java/org/bukkit/craftbukkit/block/CraftSkull.java @@ -1,28 +1,30 @@ package org.bukkit.craftbukkit.block; -import com.google.common.base.Strings; - +import net.minecraft.server.MinecraftServer; import net.minecraft.server.TileEntitySkull; +import net.minecraft.util.com.mojang.authlib.GameProfile; +import org.bukkit.OfflinePlayer; import org.bukkit.SkullType; import org.bukkit.block.Block; import org.bukkit.block.BlockFace; import org.bukkit.block.Skull; +import org.bukkit.craftbukkit.CraftOfflinePlayer; import org.bukkit.craftbukkit.CraftWorld; +import org.bukkit.craftbukkit.entity.CraftPlayer; public class CraftSkull extends CraftBlockState implements Skull { private final TileEntitySkull skull; - private String player; + private GameProfile profile; private SkullType skullType; private byte rotation; - private final int MAX_OWNER_LENGTH = 16; public CraftSkull(final Block block) { super(block); CraftWorld world = (CraftWorld) block.getWorld(); skull = (TileEntitySkull) world.getTileEntityAt(getX(), getY(), getZ()); - player = skull.getExtraType(); + profile = skull.getGameProfile(); skullType = getSkullType(skull.getSkullType()); rotation = (byte) skull.getRotation(); } @@ -140,23 +142,36 @@ public class CraftSkull extends CraftBlockState implements Skull { } public boolean hasOwner() { - return !Strings.isNullOrEmpty(player); + return profile != null; } public String getOwner() { - return player; + return profile.getName(); } public boolean setOwner(String name) { - if (name == null || name.length() > MAX_OWNER_LENGTH) { + return false; + } + + public OfflinePlayer getPlayer() { + return MinecraftServer.getServer().server.getOfflinePlayer(profile); + } + + public boolean setPlayer(OfflinePlayer player) { + GameProfile profile; + if (player instanceof CraftPlayer) { + profile = ((CraftPlayer) player).getProfile(); + } else if (player instanceof CraftOfflinePlayer) { + profile = ((CraftOfflinePlayer) player).getProfile(); + } else { return false; } - player = name; - if (skullType != SkullType.PLAYER) { - skullType = SkullType.PLAYER; + if (profile == null) { + return false; } + this.profile = profile; return true; } @@ -176,7 +191,7 @@ public class CraftSkull extends CraftBlockState implements Skull { this.skullType = skullType; if (skullType != SkullType.PLAYER) { - player = ""; + profile = null; } } @@ -185,7 +200,8 @@ public class CraftSkull extends CraftBlockState implements Skull { boolean result = super.update(force, applyPhysics); if (result) { - skull.setSkullType(getSkullType(skullType), player); + skull.setSkullType(getSkullType(skullType)); + skull.setGameProfile(profile); skull.setRotation(rotation); skull.update(); } diff --git a/src/main/java/org/bukkit/craftbukkit/entity/CraftHorse.java b/src/main/java/org/bukkit/craftbukkit/entity/CraftHorse.java index bca7a2d6..8522cad0 100644 --- a/src/main/java/org/bukkit/craftbukkit/entity/CraftHorse.java +++ b/src/main/java/org/bukkit/craftbukkit/entity/CraftHorse.java @@ -9,6 +9,8 @@ import org.bukkit.entity.EntityType; import org.bukkit.entity.Horse; import org.bukkit.inventory.HorseInventory; +import java.util.UUID; + public class CraftHorse extends CraftAnimals implements Horse { public CraftHorse(CraftServer server, EntityHorse entity) { @@ -97,28 +99,36 @@ public class CraftHorse extends CraftAnimals implements Horse { @Override public AnimalTamer getOwner() { - if (getOwnerName() == null || "".equals(getOwnerName())) return null; - return getServer().getOfflinePlayer(getOwnerName()); + if (getOwnerUUID() == null) return null; + return getServer().getOfflinePlayer(getOwnerUUID()); } @Override public void setOwner(AnimalTamer owner) { - if (owner != null && !"".equals(owner.getName())) { + if (owner != null) { setTamed(true); getHandle().setPathEntity(null); - setOwnerName(owner.getName()); + setOwnerUUID(owner.getUniqueId()); } else { setTamed(false); - setOwnerName(""); + setOwnerUUID(null); } } - public String getOwnerName() { - return getHandle().getOwnerName(); + public UUID getOwnerUUID() { + try { + return UUID.fromString(getHandle().getOwnerUUID()); + } catch (IllegalArgumentException ex) { + return null; + } } - public void setOwnerName(String name) { - getHandle().setOwnerName(name); + public void setOwnerUUID(UUID uuid) { + if (uuid == null) { + getHandle().setOwnerUUID(""); + } else { + getHandle().setOwnerUUID(uuid.toString()); + } } public HorseInventory getInventory() { diff --git a/src/main/java/org/bukkit/craftbukkit/entity/CraftPlayer.java b/src/main/java/org/bukkit/craftbukkit/entity/CraftPlayer.java index 17c16dc6..b5a54c85 100644 --- a/src/main/java/org/bukkit/craftbukkit/entity/CraftPlayer.java +++ b/src/main/java/org/bukkit/craftbukkit/entity/CraftPlayer.java @@ -13,11 +13,13 @@ import java.util.LinkedHashMap; import java.util.List; import java.util.Map; import java.util.Set; +import java.util.UUID; import java.util.logging.Level; import java.util.logging.Logger; import net.minecraft.server.*; +import net.minecraft.util.com.mojang.authlib.GameProfile; import org.apache.commons.lang.Validate; import org.apache.commons.lang.NotImplementedException; import org.bukkit.*; @@ -64,7 +66,7 @@ public class CraftPlayer extends CraftHumanEntity implements Player { private boolean hasPlayedBefore = false; private final ConversationTracker conversationTracker = new ConversationTracker(); private final Set<String> channels = new HashSet<String>(); - private final Map<String, Player> hiddenPlayers = new MapMaker().softValues().makeMap(); + private final Set<UUID> hiddenPlayers = new HashSet<UUID>(); private int hash = 0; private double health = 20; private boolean scaledHealth = false; @@ -76,9 +78,13 @@ public class CraftPlayer extends CraftHumanEntity implements Player { firstPlayed = System.currentTimeMillis(); } + public GameProfile getProfile() { + return getHandle().getProfile(); + } + @Override public boolean isOp() { - return server.getHandle().isOp(getName()); + return server.getHandle().isOp(getProfile()); } @Override @@ -86,9 +92,9 @@ public class CraftPlayer extends CraftHumanEntity implements Player { if (value == isOp()) return; if (value) { - server.getHandle().addOp(getName()); + server.getHandle().addOp(getProfile()); } else { - server.getHandle().removeOp(getName()); + server.getHandle().removeOp(getProfile()); } perm.recalculatePermissions(); @@ -732,29 +738,29 @@ public class CraftPlayer extends CraftHumanEntity implements Player { @Override public boolean isBanned() { - return server.getBanList(BanList.Type.NAME).isBanned(getName()); + return server.getBanList(BanList.Type.UUID).isBanned(getUniqueId().toString()); } @Override public void setBanned(boolean value) { if (value) { - server.getBanList(BanList.Type.NAME).addBan(getName(), null, null, null); + server.getBanList(BanList.Type.UUID).addBan(getUniqueId().toString(), null, null, null); } else { - server.getBanList(BanList.Type.NAME).pardon(getName()); + server.getBanList(BanList.Type.UUID).pardon(getUniqueId().toString()); } } @Override public boolean isWhitelisted() { - return server.getHandle().getWhitelisted().contains(getName().toLowerCase()); + return server.getHandle().isWhitelisted(getProfile()); } @Override public void setWhitelisted(boolean value) { if (value) { - server.getHandle().addWhitelist(getName().toLowerCase()); + server.getHandle().addWhitelist(getProfile()); } else { - server.getHandle().removeWhitelist(getName().toLowerCase()); + server.getHandle().removeWhitelist(getProfile()); } } @@ -872,8 +878,8 @@ public class CraftPlayer extends CraftHumanEntity implements Player { Validate.notNull(player, "hidden player cannot be null"); if (getHandle().playerConnection == null) return; if (equals(player)) return; - if (hiddenPlayers.containsKey(player.getName())) return; - hiddenPlayers.put(player.getName(), player); + if (hiddenPlayers.contains(player.getUniqueId())) return; + hiddenPlayers.add(player.getUniqueId()); //remove this player from the hidden player's EntityTrackerEntry EntityTracker tracker = ((WorldServer) entity.world).tracker; @@ -891,8 +897,8 @@ public class CraftPlayer extends CraftHumanEntity implements Player { Validate.notNull(player, "shown player cannot be null"); if (getHandle().playerConnection == null) return; if (equals(player)) return; - if (!hiddenPlayers.containsKey(player.getName())) return; - hiddenPlayers.remove(player.getName()); + if (!hiddenPlayers.contains(player.getUniqueId())) return; + hiddenPlayers.remove(player.getUniqueId()); EntityTracker tracker = ((WorldServer) entity.world).tracker; EntityPlayer other = ((CraftPlayer) player).getHandle(); @@ -904,8 +910,12 @@ public class CraftPlayer extends CraftHumanEntity implements Player { getHandle().playerConnection.sendPacket(new PacketPlayOutPlayerInfo(player.getPlayerListName(), true, getHandle().ping)); } + public void removeDisconnectingPlayer(Player player) { + hiddenPlayers.remove(player.getUniqueId()); + } + public boolean canSee(Player player) { - return !hiddenPlayers.containsKey(player.getName()); + return !hiddenPlayers.contains(player.getUniqueId()); } public Map<String, Object> serialize() { diff --git a/src/main/java/org/bukkit/craftbukkit/entity/CraftTameableAnimal.java b/src/main/java/org/bukkit/craftbukkit/entity/CraftTameableAnimal.java index f62d8bcb..d4bf3a0e 100644 --- a/src/main/java/org/bukkit/craftbukkit/entity/CraftTameableAnimal.java +++ b/src/main/java/org/bukkit/craftbukkit/entity/CraftTameableAnimal.java @@ -6,6 +6,8 @@ import org.bukkit.entity.AnimalTamer; import org.bukkit.entity.Creature; import org.bukkit.entity.Tameable; +import java.util.UUID; + public class CraftTameableAnimal extends CraftAnimals implements Tameable, Creature { public CraftTameableAnimal(CraftServer server, EntityTameableAnimal entity) { super(server, entity); @@ -16,21 +18,35 @@ public class CraftTameableAnimal extends CraftAnimals implements Tameable, Creat return (EntityTameableAnimal)super.getHandle(); } + public UUID getOwnerUUID() { + try { + return UUID.fromString(getHandle().getOwnerUUID()); + } catch (IllegalArgumentException ex) { + return null; + } + } + + public void setOwnerUUID(UUID uuid) { + if (uuid == null) { + getHandle().setOwnerUUID(""); + } else { + getHandle().setOwnerUUID(uuid.toString()); + } + } + public AnimalTamer getOwner() { - if (("").equals(getOwnerName())) return null; + if (getOwnerUUID() == null) { + return null; + } - AnimalTamer owner = getServer().getPlayerExact(getOwnerName()); + AnimalTamer owner = getServer().getPlayer(getOwnerUUID()); if (owner == null) { - owner = getServer().getOfflinePlayer(getOwnerName()); + owner = getServer().getOfflinePlayer(getOwnerUUID()); } return owner; } - public String getOwnerName() { - return getHandle().getOwnerName(); - } - public boolean isTamed() { return getHandle().isTamed(); } @@ -39,21 +55,17 @@ public class CraftTameableAnimal extends CraftAnimals implements Tameable, Creat if (tamer != null) { setTamed(true); getHandle().setPathEntity(null); - setOwnerName(tamer.getName()); + setOwnerUUID(tamer.getUniqueId()); } else { setTamed(false); - setOwnerName(""); + setOwnerUUID(null); } } - public void setOwnerName(String ownerName) { - getHandle().setOwnerName(ownerName == null ? "" : ownerName); - } - public void setTamed(boolean tame) { getHandle().setTamed(tame); if (!tame) { - setOwnerName(""); + setOwnerUUID(null); } } diff --git a/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java b/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java index 2911d601..4cc25f2c 100644 --- a/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java +++ b/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java @@ -85,7 +85,7 @@ public class CraftEventFactory { if (world.getHandle().dimension != 0) return true; if (spawnSize <= 0) return true; - if (((CraftServer) Bukkit.getServer()).getHandle().getOPs().isEmpty()) return true; + if (((CraftServer) Bukkit.getServer()).getHandle().getOPs().d()) return true; // Should be isEmpty if (player.isOp()) return true; ChunkCoordinates chunkcoordinates = worldServer.getSpawn(); |