From 8cfda81aa19c178d605f6967b10b2d68fb968783 Mon Sep 17 00:00:00 2001 From: Spottedleaf Date: Tue, 9 Jul 2019 02:18:54 -0700 Subject: [PATCH] Remove DataWatcher Locking The lock in DataWatcher is used to prevent concurrent modifications, however any modifications to this map only occur on initialization of an Entity in its constructor. Every other access is through a readlock, which allows the threads to pass if there is no thread holding the writelock. Since the writelock is only obtained in the constructor of the Entity, the further readlocks are actually useless. This patch also changes the entries map to be fastutil int2objectopenhashmap for performance. diff --git a/src/main/java/net/minecraft/network/syncher/DataWatcher.java b/src/main/java/net/minecraft/network/syncher/DataWatcher.java index 839e2dce4..5276be007 100644 --- a/src/main/java/net/minecraft/network/syncher/DataWatcher.java +++ b/src/main/java/net/minecraft/network/syncher/DataWatcher.java @@ -33,7 +33,7 @@ public class DataWatcher { private static final int MAX_ID_VALUE = 254; private final Entity entity; private final Int2ObjectMap> itemsById = new Int2ObjectOpenHashMap(); - private final ReadWriteLock lock = new ReentrantReadWriteLock(); + // private final ReadWriteLock lock = new ReentrantReadWriteLock(); // Spigot - not required private boolean isEmpty = true; private boolean isDirty; @@ -81,7 +81,9 @@ public class DataWatcher { } } + public boolean registrationLocked; // Spigot public void define(DataWatcherObject datawatcherobject, T t0) { + if (this.registrationLocked) throw new IllegalStateException("Registering datawatcher object after entity initialization"); // Spigot int i = datawatcherobject.getId(); if (i > 254) { @@ -100,13 +102,15 @@ public class DataWatcher { private void createDataItem(DataWatcherObject datawatcherobject, T t0) { DataWatcher.Item datawatcher_item = new DataWatcher.Item<>(datawatcherobject, t0); - this.lock.writeLock().lock(); + // this.lock.writeLock().lock(); // Spigot - not required this.itemsById.put(datawatcherobject.getId(), datawatcher_item); this.isEmpty = false; - this.lock.writeLock().unlock(); + // this.lock.writeLock().unlock(); // Spigot - not required } private DataWatcher.Item getItem(DataWatcherObject datawatcherobject) { + // Spigot start + /* this.lock.readLock().lock(); DataWatcher.Item datawatcher_item; @@ -124,6 +128,9 @@ public class DataWatcher { } return datawatcher_item; + */ + return (DataWatcher.Item) this.itemsById.get(datawatcherobject.getId()); + // Spigot end } public T get(DataWatcherObject datawatcherobject) { @@ -172,7 +179,7 @@ public class DataWatcher { List> list = null; if (this.isDirty) { - this.lock.readLock().lock(); + // this.lock.readLock().lock(); // Spigot - not required ObjectIterator objectiterator = this.itemsById.values().iterator(); while (objectiterator.hasNext()) { @@ -188,7 +195,7 @@ public class DataWatcher { } } - this.lock.readLock().unlock(); + // this.lock.readLock().unlock(); // Spigot - not required } this.isDirty = false; @@ -199,7 +206,7 @@ public class DataWatcher { public List> getAll() { List> list = null; - this.lock.readLock().lock(); + // this.lock.readLock().lock(); // Spigot - not required DataWatcher.Item datawatcher_item; @@ -210,7 +217,7 @@ public class DataWatcher { } } - this.lock.readLock().unlock(); + // this.lock.readLock().unlock(); // Spigot - not required return list; } @@ -256,7 +263,7 @@ public class DataWatcher { } public void assignValues(List> list) { - this.lock.writeLock().lock(); + // this.lock.writeLock().lock(); // Spigot - not required try { Iterator iterator = list.iterator(); @@ -271,7 +278,7 @@ public class DataWatcher { } } } finally { - this.lock.writeLock().unlock(); + // this.lock.writeLock().unlock(); // Spigot - not required } this.isDirty = true; @@ -291,7 +298,7 @@ public class DataWatcher { public void clearDirty() { this.isDirty = false; - this.lock.readLock().lock(); + // this.lock.readLock().lock(); // Spigot - not required ObjectIterator objectiterator = this.itemsById.values().iterator(); while (objectiterator.hasNext()) { @@ -300,7 +307,7 @@ public class DataWatcher { datawatcher_item.setDirty(false); } - this.lock.readLock().unlock(); + // this.lock.readLock().unlock(); // Spigot - not required } public static class Item { diff --git a/src/main/java/net/minecraft/world/entity/Entity.java b/src/main/java/net/minecraft/world/entity/Entity.java index 2f63a9ee7..52edfbb84 100644 --- a/src/main/java/net/minecraft/world/entity/Entity.java +++ b/src/main/java/net/minecraft/world/entity/Entity.java @@ -360,6 +360,7 @@ public abstract class Entity implements INamableTileEntity, EntityAccess, IComma this.entityData.define(Entity.DATA_POSE, EntityPose.STANDING); this.entityData.define(Entity.DATA_TICKS_FROZEN, 0); this.defineSynchedData(); + this.getEntityData().registrationLocked = true; // Spigot this.setPos(0.0D, 0.0D, 0.0D); this.eyeHeight = this.getEyeHeight(EntityPose.STANDING, this.dimensions); } -- 2.34.1