Skip to content

Commit 86487a8

Browse files
committed
1.1.16: Override registered packets
1 parent 85b0af2 commit 86487a8

5 files changed

Lines changed: 59 additions & 8 deletions

File tree

README.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@ Test server: [``ely.su``](https://hotmc.ru/minecraft-server-203216)
5353
<dependency>
5454
<groupId>net.elytrium.limboapi</groupId>
5555
<artifactId>api</artifactId>
56-
<version>1.1.15</version>
56+
<version>1.1.16</version>
5757
<scope>provided</scope>
5858
</dependency>
5959
</dependencies>
@@ -70,7 +70,7 @@ Test server: [``ely.su``](https://hotmc.ru/minecraft-server-203216)
7070
}
7171
7272
dependencies {
73-
compileOnly("net.elytrium.limboapi:api:1.1.15")
73+
compileOnly("net.elytrium.limboapi:api:1.1.16")
7474
}
7575
```
7676

VERSION

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
1.1.15
1+
1.1.16

api/src/main/java/net/elytrium/limboapi/api/utils/OverlayMap.java

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313

1414
public abstract class OverlayMap<K, V> implements Map<K, V> {
1515

16+
protected boolean override = false;
1617
protected final Map<K, V> parent;
1718
protected final Map<K, V> overlay;
1819

@@ -33,11 +34,19 @@ public boolean isEmpty() {
3334

3435
@Override
3536
public boolean containsKey(Object o) {
37+
if (this.override) {
38+
return this.overlay.containsKey(o);
39+
}
40+
3641
return this.parent.containsKey(o) || this.overlay.containsKey(o);
3742
}
3843

3944
@Override
4045
public boolean containsValue(Object o) {
46+
if (this.override) {
47+
return this.overlay.containsValue(o);
48+
}
49+
4150
return this.parent.containsValue(o) || this.overlay.containsValue(o);
4251
}
4352

@@ -71,4 +80,12 @@ public void putAll(@NotNull Map<? extends K, ? extends V> map) {
7180
public void clear() {
7281
this.overlay.clear();
7382
}
83+
84+
public boolean isOverride() {
85+
return this.override;
86+
}
87+
88+
public void setOverride(boolean override) {
89+
this.override = override;
90+
}
7491
}

build.gradle

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ allprojects {
1313
apply(plugin: "org.cadixdev.licenser")
1414

1515
setGroup("net.elytrium.limboapi")
16-
setVersion("1.1.15")
16+
setVersion("1.1.16")
1717

1818
compileJava {
1919
getOptions().setEncoding("UTF-8")

plugin/src/main/java/net/elytrium/limboapi/protocol/LimboProtocol.java

Lines changed: 38 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -31,11 +31,15 @@
3131
import java.util.Arrays;
3232
import java.util.Collections;
3333
import java.util.EnumMap;
34+
import java.util.List;
3435
import java.util.Map;
3536
import java.util.function.Supplier;
37+
import java.util.stream.Collectors;
38+
import java.util.stream.Stream;
3639
import net.elytrium.commons.utils.reflection.ReflectionException;
3740
import net.elytrium.limboapi.api.protocol.PacketDirection;
3841
import net.elytrium.limboapi.api.protocol.packets.PacketMapping;
42+
import net.elytrium.limboapi.api.utils.OverlayMap;
3943
import net.elytrium.limboapi.protocol.packets.c2s.MoveOnGroundOnlyPacket;
4044
import net.elytrium.limboapi.protocol.packets.c2s.MovePacket;
4145
import net.elytrium.limboapi.protocol.packets.c2s.MovePositionOnlyPacket;
@@ -67,8 +71,11 @@ public class LimboProtocol {
6771

6872
public static final String READ_TIMEOUT = "limboapi-read-timeout";
6973

74+
public static final MethodHandle VERSIONS_GETTER;
7075
public static final Field VERSIONS_FIELD;
76+
public static final MethodHandle PACKET_ID_TO_SUPPLIER_GETTER;
7177
public static final Field PACKET_ID_TO_SUPPLIER_FIELD;
78+
public static final MethodHandle PACKET_CLASS_TO_ID_GETTER;
7279
public static final Field PACKET_CLASS_TO_ID_FIELD;
7380
public static final StateRegistry.PacketRegistry PLAY_CLIENTBOUND_REGISTRY;
7481
public static final StateRegistry.PacketRegistry PLAY_SERVERBOUND_REGISTRY;
@@ -85,12 +92,18 @@ public class LimboProtocol {
8592

8693
LIMBO_STATE_REGISTRY = (StateRegistry) UNSAFE.allocateInstance(StateRegistry.class);
8794

95+
VERSIONS_GETTER = MethodHandles.privateLookupIn(StateRegistry.PacketRegistry.class, MethodHandles.lookup())
96+
.findGetter(StateRegistry.PacketRegistry.class, "versions", Map.class);
8897
VERSIONS_FIELD = StateRegistry.PacketRegistry.class.getDeclaredField("versions");
8998
VERSIONS_FIELD.setAccessible(true);
9099

100+
PACKET_ID_TO_SUPPLIER_GETTER = MethodHandles.privateLookupIn(StateRegistry.PacketRegistry.ProtocolRegistry.class, MethodHandles.lookup())
101+
.findGetter(StateRegistry.PacketRegistry.ProtocolRegistry.class, "packetIdToSupplier", IntObjectMap.class);
91102
PACKET_ID_TO_SUPPLIER_FIELD = StateRegistry.PacketRegistry.ProtocolRegistry.class.getDeclaredField("packetIdToSupplier");
92103
PACKET_ID_TO_SUPPLIER_FIELD.setAccessible(true);
93104

105+
PACKET_CLASS_TO_ID_GETTER = MethodHandles.privateLookupIn(StateRegistry.PacketRegistry.ProtocolRegistry.class, MethodHandles.lookup())
106+
.findGetter(StateRegistry.PacketRegistry.ProtocolRegistry.class, "packetClassToId", Object2IntMap.class);
94107
PACKET_CLASS_TO_ID_FIELD = StateRegistry.PacketRegistry.ProtocolRegistry.class.getDeclaredField("packetClassToId");
95108
PACKET_CLASS_TO_ID_FIELD.setAccessible(true);
96109

@@ -121,7 +134,7 @@ public class LimboProtocol {
121134
}
122135

123136
private static void overlayRegistry(StateRegistry stateRegistry,
124-
String registryName, StateRegistry.PacketRegistry playRegistry) throws ReflectiveOperationException {
137+
String registryName, StateRegistry.PacketRegistry playRegistry) throws Throwable {
125138
StateRegistry.PacketRegistry registry = (StateRegistry.PacketRegistry) UNSAFE.allocateInstance(StateRegistry.PacketRegistry.class);
126139

127140
Field directionField = StateRegistry.PacketRegistry.class.getDeclaredField("direction");
@@ -133,7 +146,8 @@ private static void overlayRegistry(StateRegistry stateRegistry,
133146

134147
// Overlay packets from PLAY state registry.
135148
// P.S. I hate it when someone uses var in code, but there I had no choice.
136-
var playProtocolRegistryVersions = (Map<ProtocolVersion, StateRegistry.PacketRegistry.ProtocolRegistry>) VERSIONS_FIELD.get(playRegistry);
149+
var playProtocolRegistryVersions =
150+
(Map<ProtocolVersion, StateRegistry.PacketRegistry.ProtocolRegistry>) VERSIONS_GETTER.invokeExact(playRegistry);
137151
Map<ProtocolVersion, StateRegistry.PacketRegistry.ProtocolRegistry> versions = new EnumMap<>(ProtocolVersion.class);
138152
for (ProtocolVersion version : ProtocolVersion.values()) {
139153
if (!version.isLegacy() && !version.isUnknown()) {
@@ -142,10 +156,10 @@ private static void overlayRegistry(StateRegistry stateRegistry,
142156

143157
versionField.set(protoRegistry, version);
144158

145-
var playPacketIDToSupplier = (IntObjectMap<Supplier<? extends MinecraftPacket>>) PACKET_ID_TO_SUPPLIER_FIELD.get(playProtoRegistry);
159+
var playPacketIDToSupplier = (IntObjectMap<Supplier<? extends MinecraftPacket>>) PACKET_ID_TO_SUPPLIER_GETTER.invokeExact(playProtoRegistry);
146160
PACKET_ID_TO_SUPPLIER_FIELD.set(protoRegistry, new OverlayIntObjectMap<>(playPacketIDToSupplier, new IntObjectHashMap<>(16, 0.5F)));
147161

148-
var playPacketClassToID = (Object2IntMap<Class<? extends MinecraftPacket>>) PACKET_CLASS_TO_ID_FIELD.get(playProtoRegistry);
162+
var playPacketClassToID = (Object2IntMap<Class<? extends MinecraftPacket>>) PACKET_CLASS_TO_ID_GETTER.invokeExact(playProtoRegistry);
149163
Object2IntMap<Class<? extends MinecraftPacket>> packetClassToID = new Object2IntOpenHashMap<>(16, 0.5F);
150164
packetClassToID.defaultReturnValue(playPacketClassToID.defaultReturnValue());
151165
PACKET_CLASS_TO_ID_FIELD.set(protoRegistry, new OverlayObject2IntMap<>(playPacketClassToID, packetClassToID));
@@ -448,7 +462,27 @@ public static void register(StateRegistry stateRegistry,
448462
public static void register(StateRegistry.PacketRegistry registry,
449463
Class<?> packetClass, Supplier<?> packetSupplier, StateRegistry.PacketMapping... mappings) {
450464
try {
465+
var versions = (Map<ProtocolVersion, StateRegistry.PacketRegistry.ProtocolRegistry>) VERSIONS_GETTER.invokeExact(registry);
466+
List<OverlayMap<?, ?>> overlayMaps = versions.values().stream().flatMap(protocolRegistry -> {
467+
try {
468+
var idToSupplier = (IntObjectMap<Supplier<? extends MinecraftPacket>>) PACKET_ID_TO_SUPPLIER_GETTER.invokeExact(protocolRegistry);
469+
var classToId = (Object2IntMap<Class<? extends MinecraftPacket>>) PACKET_CLASS_TO_ID_GETTER.invokeExact(protocolRegistry);
470+
if (idToSupplier instanceof OverlayMap<?, ?> && classToId instanceof OverlayMap<?, ?>) {
471+
return Stream.of(
472+
(OverlayMap<?, ?>) idToSupplier,
473+
(OverlayMap<?, ?>) classToId
474+
);
475+
} else {
476+
return Stream.empty();
477+
}
478+
} catch (Throwable e) {
479+
throw new ReflectionException(e);
480+
}
481+
}).collect(Collectors.toList());
482+
483+
overlayMaps.forEach(overlayMap -> overlayMap.setOverride(true));
451484
REGISTER_METHOD.invokeExact(registry, packetClass, packetSupplier, mappings);
485+
overlayMaps.forEach(overlayMap -> overlayMap.setOverride(false));
452486
} catch (Throwable e) {
453487
throw new ReflectionException(e);
454488
}

0 commit comments

Comments
 (0)