-
-
Notifications
You must be signed in to change notification settings - Fork 259
/
PacketTypeLookup.java
174 lines (156 loc) · 7.4 KB
/
PacketTypeLookup.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
package com.comphenix.protocol;
import java.util.Collection;
import java.util.Collections;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import com.comphenix.protocol.PacketType.Protocol;
import com.comphenix.protocol.PacketType.Sender;
import com.comphenix.protocol.collections.IntegerMap;
import com.google.common.base.Preconditions;
import com.google.common.collect.HashMultimap;
import com.google.common.collect.Multimap;
/**
* Retrieve a packet type based on its version and ID, optionally with protocol and sender too.
* @author Kristian
*/
class PacketTypeLookup {
public static class ProtocolSenderLookup {
// Unroll lookup for performance reasons
public final IntegerMap<PacketType> HANDSHAKE_CLIENT = new IntegerMap<>();
public final IntegerMap<PacketType> HANDSHAKE_SERVER = new IntegerMap<>();
public final IntegerMap<PacketType> GAME_CLIENT = new IntegerMap<>();
public final IntegerMap<PacketType> GAME_SERVER = new IntegerMap<>();
public final IntegerMap<PacketType> STATUS_CLIENT = new IntegerMap<>();
public final IntegerMap<PacketType> STATUS_SERVER = new IntegerMap<>();
public final IntegerMap<PacketType> LOGIN_CLIENT = new IntegerMap<>();
public final IntegerMap<PacketType> LOGIN_SERVER = new IntegerMap<>();
public final IntegerMap<PacketType> CONFIGURATION_CLIENT = new IntegerMap<>();
public final IntegerMap<PacketType> CONFIGURATION_SERVER = new IntegerMap<>();
/**
* Retrieve the correct integer map for a specific protocol and sender.
* @param protocol - the protocol.
* @param sender - the sender.
* @return The integer map of packets.
*/
public IntegerMap<PacketType> getMap(Protocol protocol, Sender sender) {
switch (protocol) {
case HANDSHAKING:
return sender == Sender.CLIENT ? HANDSHAKE_CLIENT : HANDSHAKE_SERVER;
case PLAY:
return sender == Sender.CLIENT ? GAME_CLIENT : GAME_SERVER;
case STATUS:
return sender == Sender.CLIENT ? STATUS_CLIENT : STATUS_SERVER;
case LOGIN:
return sender == Sender.CLIENT ? LOGIN_CLIENT : LOGIN_SERVER;
case CONFIGURATION:
return sender == Sender.CLIENT ? CONFIGURATION_CLIENT : CONFIGURATION_SERVER;
default:
throw new IllegalArgumentException("Unable to find protocol " + protocol);
}
}
}
public static class ClassLookup {
// Unroll lookup for performance reasons
public final Map<String, PacketType> HANDSHAKE_CLIENT = new ConcurrentHashMap<>();
public final Map<String, PacketType> HANDSHAKE_SERVER = new ConcurrentHashMap<>();
public final Map<String, PacketType> GAME_CLIENT = new ConcurrentHashMap<>();
public final Map<String, PacketType> GAME_SERVER = new ConcurrentHashMap<>();
public final Map<String, PacketType> STATUS_CLIENT = new ConcurrentHashMap<>();
public final Map<String, PacketType> STATUS_SERVER = new ConcurrentHashMap<>();
public final Map<String, PacketType> LOGIN_CLIENT = new ConcurrentHashMap<>();
public final Map<String, PacketType> LOGIN_SERVER = new ConcurrentHashMap<>();
public final Map<String, PacketType> CONFIGURATION_CLIENT = new ConcurrentHashMap<>();
public final Map<String, PacketType> CONFIGURATION_SERVER = new ConcurrentHashMap<>();
/**
* Retrieve the correct integer map for a specific protocol and sender.
* @param protocol - the protocol.
* @param sender - the sender.
* @return The integer map of packets.
*/
public Map<String, PacketType> getMap(Protocol protocol, Sender sender) {
switch (protocol) {
case HANDSHAKING:
return sender == Sender.CLIENT ? HANDSHAKE_CLIENT : HANDSHAKE_SERVER;
case PLAY:
return sender == Sender.CLIENT ? GAME_CLIENT : GAME_SERVER;
case STATUS:
return sender == Sender.CLIENT ? STATUS_CLIENT : STATUS_SERVER;
case LOGIN:
return sender == Sender.CLIENT ? LOGIN_CLIENT : LOGIN_SERVER;
case CONFIGURATION:
return sender == Sender.CLIENT ? CONFIGURATION_CLIENT : CONFIGURATION_SERVER;
default:
throw new IllegalArgumentException("Unable to find protocol " + protocol);
}
}
}
// Packets for 1.7.2
private final ProtocolSenderLookup idLookup = new ProtocolSenderLookup();
// Packets for 1.8+
private final ClassLookup classLookup = new ClassLookup();
// Packets based on name
private final Multimap<String, PacketType> nameLookup = HashMultimap.create();
/**
* Add a collection of packet types to the lookup.
* @param types - the types to add.
*/
public PacketTypeLookup addPacketTypes(Iterable<? extends PacketType> types) {
Preconditions.checkNotNull(types, "types cannot be NULL");
for (PacketType type : types) {
// Skip unknown current packets
if (type.getCurrentId() != PacketType.UNKNOWN_PACKET) {
idLookup.getMap(type.getProtocol(), type.getSender()).put(type.getCurrentId(), type);
classLookup.getMap(type.getProtocol(), type.getSender()).put(type.getClassNames().get(0), type);
}
nameLookup.put(type.name(), type);
}
return this;
}
/**
* Retrieve a packet type from a legacy (1.6.4 and below) packet ID.
* @param packetId - the legacy packet ID.
* @return The corresponding packet type, or NULL if not found.
* @deprecated no longer works and will always return null
*/
@Deprecated
public PacketType getFromLegacy(int packetId) {
return null;
}
/**
* Retrieve an unmodifiable view of all the packet types with this name.
* @param name - the name.
* @return The packet types, usually one.
*/
public Collection<PacketType> getFromName(String name) {
return Collections.unmodifiableCollection(nameLookup.get(name));
}
/**
* Retrieve a packet type from a legacy (1.6.4 and below) packet ID.
* @param packetId - the legacy packet ID.
* @param preference - which packet type to look for first.
* @return The corresponding packet type, or NULL if not found.
* @deprecated no longer works and will always return null
*/
@Deprecated
public PacketType getFromLegacy(int packetId, Sender preference) {
return null;
}
/**
* Retrieve a packet type from a protocol, sender and packet ID.
* @param protocol - the current protocol.
* @param sender - the sender.
* @param packetId - the packet ID.
* @return The corresponding packet type, or NULL if not found.
* @deprecated IDs are no longer reliable
*/
@Deprecated
public PacketType getFromCurrent(Protocol protocol, Sender sender, int packetId) {
return idLookup.getMap(protocol, sender).get(packetId);
}
public PacketType getFromCurrent(Protocol protocol, Sender sender, String name) {
return classLookup.getMap(protocol, sender).get(name);
}
public ClassLookup getClassLookup() {
return classLookup;
}
}