Incredibly difficult bug to track down.
Forgot to remove the "override" flag on cancelled packets when they're sent again.
Dieser Commit ist enthalten in:
Ursprung
0cff9d1243
Commit
801bf81f15
@ -74,22 +74,22 @@ public class AsyncFilterManager implements AsynchronousManager {
|
|||||||
ListeningWhitelist receivingWhitelist = listener.getReceivingWhitelist();
|
ListeningWhitelist receivingWhitelist = listener.getReceivingWhitelist();
|
||||||
|
|
||||||
// We need a synchronized listener to get the ball rolling
|
// We need a synchronized listener to get the ball rolling
|
||||||
boolean needNoOp = true;
|
boolean hasListener = true;
|
||||||
|
|
||||||
// Add listener to either or both processing queue
|
// Add listener to either or both processing queue
|
||||||
if (hasValidWhitelist(sendingWhitelist)) {
|
if (hasValidWhitelist(sendingWhitelist)) {
|
||||||
PacketFilterManager.verifyWhitelist(listener, sendingWhitelist);
|
PacketFilterManager.verifyWhitelist(listener, sendingWhitelist);
|
||||||
serverProcessingQueue.addListener(handler, sendingWhitelist);
|
serverProcessingQueue.addListener(handler, sendingWhitelist);
|
||||||
needNoOp &= hasPacketListener(sendingWhitelist);
|
hasListener &= hasPacketListener(sendingWhitelist);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (hasValidWhitelist(receivingWhitelist)) {
|
if (hasValidWhitelist(receivingWhitelist)) {
|
||||||
PacketFilterManager.verifyWhitelist(listener, receivingWhitelist);
|
PacketFilterManager.verifyWhitelist(listener, receivingWhitelist);
|
||||||
clientProcessingQueue.addListener(handler, receivingWhitelist);
|
clientProcessingQueue.addListener(handler, receivingWhitelist);
|
||||||
needNoOp &= hasPacketListener(receivingWhitelist);
|
hasListener &= hasPacketListener(receivingWhitelist);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (needNoOp) {
|
if (!hasListener) {
|
||||||
handler.setNullPacketListener(new NullPacketListener(listener));
|
handler.setNullPacketListener(new NullPacketListener(listener));
|
||||||
manager.addPacketListener(handler.getNullPacketListener());
|
manager.addPacketListener(handler.getNullPacketListener());
|
||||||
}
|
}
|
||||||
|
@ -97,8 +97,9 @@ class PacketSendingQueue {
|
|||||||
AsyncMarker marker = current.getAsyncMarker();
|
AsyncMarker marker = current.getAsyncMarker();
|
||||||
|
|
||||||
if (marker.isProcessed() || marker.hasExpired()) {
|
if (marker.isProcessed() || marker.hasExpired()) {
|
||||||
if (marker.isProcessed() && !current.isCancelled())
|
if (marker.isProcessed() && !current.isCancelled()) {
|
||||||
sendPacket(current);
|
sendPacket(current);
|
||||||
|
}
|
||||||
|
|
||||||
sendingQueue.poll();
|
sendingQueue.poll();
|
||||||
continue;
|
continue;
|
||||||
|
@ -399,6 +399,9 @@ public final class PacketFilterManager implements ProtocolManager {
|
|||||||
PlayerInjector injector = getInjector(sender);
|
PlayerInjector injector = getInjector(sender);
|
||||||
Packet mcPacket = packet.getHandle();
|
Packet mcPacket = packet.getHandle();
|
||||||
|
|
||||||
|
// Make sure the packet isn't cancelled
|
||||||
|
packetInjector.undoCancel(packet.getID(), mcPacket);
|
||||||
|
|
||||||
if (filters) {
|
if (filters) {
|
||||||
mcPacket = injector.handlePacketRecieved(mcPacket);
|
mcPacket = injector.handlePacketRecieved(mcPacket);
|
||||||
}
|
}
|
||||||
|
@ -23,6 +23,7 @@ import java.lang.reflect.InvocationTargetException;
|
|||||||
import java.lang.reflect.Method;
|
import java.lang.reflect.Method;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
|
import java.util.concurrent.ConcurrentHashMap;
|
||||||
|
|
||||||
import org.bukkit.entity.Player;
|
import org.bukkit.entity.Player;
|
||||||
|
|
||||||
@ -52,6 +53,9 @@ class PacketInjector {
|
|||||||
// Allows us to determine the sender
|
// Allows us to determine the sender
|
||||||
private Map<DataInputStream, Player> playerLookup;
|
private Map<DataInputStream, Player> playerLookup;
|
||||||
|
|
||||||
|
// Allows us to look up read packet injectors
|
||||||
|
private Map<Integer, ReadPacketModifier> readModifier;
|
||||||
|
|
||||||
// Class loader
|
// Class loader
|
||||||
private ClassLoader classLoader;
|
private ClassLoader classLoader;
|
||||||
|
|
||||||
@ -61,9 +65,24 @@ class PacketInjector {
|
|||||||
this.classLoader = classLoader;
|
this.classLoader = classLoader;
|
||||||
this.manager = manager;
|
this.manager = manager;
|
||||||
this.playerLookup = playerLookup;
|
this.playerLookup = playerLookup;
|
||||||
|
this.readModifier = new ConcurrentHashMap<Integer, ReadPacketModifier>();
|
||||||
initialize();
|
initialize();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Undo a packet cancel.
|
||||||
|
* @param id - the id of the packet.
|
||||||
|
* @param packet - packet to uncancel.
|
||||||
|
*/
|
||||||
|
public void undoCancel(Integer id, Packet packet) {
|
||||||
|
ReadPacketModifier modifier = readModifier.get(id);
|
||||||
|
|
||||||
|
// Cancelled packets are represented with NULL
|
||||||
|
if (modifier != null && modifier.getOverride(packet) == null) {
|
||||||
|
modifier.removeOverride(packet);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private void initialize() throws IllegalAccessException {
|
private void initialize() throws IllegalAccessException {
|
||||||
if (intHashMap == null) {
|
if (intHashMap == null) {
|
||||||
// We're looking for the first static field with a Minecraft-object. This should be a IntHashMap.
|
// We're looking for the first static field with a Minecraft-object. This should be a IntHashMap.
|
||||||
@ -109,10 +128,12 @@ class PacketInjector {
|
|||||||
ex.setClassLoader(classLoader);
|
ex.setClassLoader(classLoader);
|
||||||
Class proxy = ex.createClass();
|
Class proxy = ex.createClass();
|
||||||
|
|
||||||
|
// Create the proxy handler
|
||||||
|
ReadPacketModifier modifier = new ReadPacketModifier(packetID, this);
|
||||||
|
readModifier.put(packetID, modifier);
|
||||||
|
|
||||||
// Add a static reference
|
// Add a static reference
|
||||||
Enhancer.registerStaticCallbacks(proxy, new Callback[] {
|
Enhancer.registerStaticCallbacks(proxy, new Callback[] { modifier });
|
||||||
new ReadPacketModifier(packetID, this)
|
|
||||||
});
|
|
||||||
|
|
||||||
try {
|
try {
|
||||||
// Override values
|
// Override values
|
||||||
@ -147,6 +168,7 @@ class PacketInjector {
|
|||||||
|
|
||||||
putMethod.invoke(intHashMap, packetID, old);
|
putMethod.invoke(intHashMap, packetID, old);
|
||||||
previous.remove(packetID);
|
previous.remove(packetID);
|
||||||
|
readModifier.remove(packetID);
|
||||||
registry.remove(proxy);
|
registry.remove(proxy);
|
||||||
overwritten.remove(packetID);
|
overwritten.remove(packetID);
|
||||||
return true;
|
return true;
|
||||||
|
@ -45,6 +45,23 @@ class ReadPacketModifier implements MethodInterceptor {
|
|||||||
this.packetID = packetID;
|
this.packetID = packetID;
|
||||||
this.packetInjector = packetInjector;
|
this.packetInjector = packetInjector;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Remove any packet overrides.
|
||||||
|
* @param packet - the packet to rever
|
||||||
|
*/
|
||||||
|
public void removeOverride(Packet packet) {
|
||||||
|
override.remove(packet);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Retrieve the packet that overrides the methods of the given packet.
|
||||||
|
* @param packet - the given packet.
|
||||||
|
* @return Overriden object.
|
||||||
|
*/
|
||||||
|
public Object getOverride(Packet packet) {
|
||||||
|
return override.get(packet);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Object intercept(Object thisObj, Method method, Object[] args, MethodProxy proxy) throws Throwable {
|
public Object intercept(Object thisObj, Method method, Object[] args, MethodProxy proxy) throws Throwable {
|
||||||
|
In neuem Issue referenzieren
Einen Benutzer sperren