Code polish

This commit is contained in:
nathan 2014-09-22 23:59:03 +02:00
parent ac4699a8c9
commit 7603b96d5e
8 changed files with 125 additions and 81 deletions

View File

@ -135,6 +135,7 @@ public abstract class EndPoint {
final SecureRandom secureRandom; final SecureRandom secureRandom;
SettingsStore propertyStore; SettingsStore propertyStore;
boolean disableRemoteKeyValidation;
public EndPoint(String name, ConnectionOptions options) throws InitializationException, SecurityException { public EndPoint(String name, ConnectionOptions options) throws InitializationException, SecurityException {
@ -211,6 +212,19 @@ public abstract class EndPoint {
Runtime.getRuntime().addShutdownHook(this.shutdownHook); Runtime.getRuntime().addShutdownHook(this.shutdownHook);
} }
public void disableRemoteKeyValidation() {
Logger logger2 = this.logger;
if (isConnected()) {
logger2.error("Cannot disable the remote key validation after this endpoint is connected!");
} else {
if (logger2.isInfoEnabled()) {
logger2.info("WARNING: Disabling remote key validation is a security risk!!");
}
this.disableRemoteKeyValidation = true;
}
}
/** /**
* Returns the property store used by this endpoint. The property store can store via properties, * Returns the property store used by this endpoint. The property store can store via properties,
* a database, etc, or can be a "null" property store, which does nothing * a database, etc, or can be a "null" property store, which does nothing
@ -265,9 +279,9 @@ public abstract class EndPoint {
/** /**
* Return the connection status of this endpoint. * Return the connection status of this endpoint.
* <p> * <p>
* Once a server has connected to ANY client, it will always return true. * Once a server has connected to ANY client, it will always return true until server.close() is called
*/ */
public boolean isConnected() { public final boolean isConnected() {
return this.isConnected.get(); return this.isConnected.get();
} }
@ -328,8 +342,9 @@ public abstract class EndPoint {
inEventThread = false; inEventThread = false;
// we need to test to see if our current thread is in ANY of the event group threads. If it IS, then we risk deadlocking! // we need to test to see if our current thread is in ANY of the event group threads. If it IS, then we risk deadlocking!
synchronized (this.eventLoopGroups) { List<EventLoopGroup> eventLoopGroups2 = this.eventLoopGroups;
for (EventLoopGroup loopGroup : this.eventLoopGroups) { synchronized (eventLoopGroups2) {
for (EventLoopGroup loopGroup : eventLoopGroups2) {
if (!inEventThread) { if (!inEventThread) {
inEventThread = checkInEventGroup(currentThread, loopGroup); inEventThread = checkInEventGroup(currentThread, loopGroup);
break; break;
@ -380,8 +395,9 @@ public abstract class EndPoint {
// Sometimes there might be "lingering" connections (ie, halfway though registration) that need to be closed. // Sometimes there might be "lingering" connections (ie, halfway though registration) that need to be closed.
long maxShutdownWaitTimeInMilliSeconds = EndPoint.maxShutdownWaitTimeInMilliSeconds; long maxShutdownWaitTimeInMilliSeconds = EndPoint.maxShutdownWaitTimeInMilliSeconds;
RegistrationWrapper registrationWrapper2 = this.registrationWrapper;
try { try {
IntMap<MetaChannel> channelMap = this.registrationWrapper.getAndLockChannelMap(); IntMap<MetaChannel> channelMap = registrationWrapper2.getAndLockChannelMap();
Entries<MetaChannel> entries = channelMap.entries(); Entries<MetaChannel> entries = channelMap.entries();
while (entries.hasNext()) { while (entries.hasNext()) {
MetaChannel metaChannel = entries.next().value; MetaChannel metaChannel = entries.next().value;
@ -391,7 +407,7 @@ public abstract class EndPoint {
channelMap.clear(); channelMap.clear();
} finally { } finally {
this.registrationWrapper.releaseChannelMap(); registrationWrapper2.releaseChannelMap();
} }
// shutdown the database store // shutdown the database store

View File

@ -142,6 +142,10 @@ public class RegistrationWrapper implements UdpServer {
} }
public boolean validateRemoteServerAddress(InetSocketAddress tcpRemoteServer, ECPublicKeyParameters publicKey) throws SecurityException { public boolean validateRemoteServerAddress(InetSocketAddress tcpRemoteServer, ECPublicKeyParameters publicKey) throws SecurityException {
if (this.endPoint.disableRemoteKeyValidation) {
return true;
}
InetAddress address = tcpRemoteServer.getAddress(); InetAddress address = tcpRemoteServer.getAddress();
byte[] hostAddress = address.getAddress(); byte[] hostAddress = address.getAddress();

View File

@ -142,14 +142,16 @@ public class RegistrationRemoteHandlerClientTCP extends RegistrationRemoteHandle
public void channelRead(ChannelHandlerContext context, Object message) throws Exception { public void channelRead(ChannelHandlerContext context, Object message) throws Exception {
Channel channel = context.channel(); Channel channel = context.channel();
RegistrationWrapper registrationWrapper2 = this.registrationWrapper;
Logger logger2 = this.logger;
if (message instanceof Registration) { if (message instanceof Registration) {
// make sure this connection was properly registered in the map. (IT SHOULD BE) // make sure this connection was properly registered in the map. (IT SHOULD BE)
MetaChannel metaChannel = null; MetaChannel metaChannel = null;
try { try {
IntMap<MetaChannel> channelMap = this.registrationWrapper.getAndLockChannelMap(); IntMap<MetaChannel> channelMap = registrationWrapper2.getAndLockChannelMap();
metaChannel = channelMap.get(channel.hashCode()); metaChannel = channelMap.get(channel.hashCode());
} finally { } finally {
this.registrationWrapper.releaseChannelMap(); registrationWrapper2.releaseChannelMap();
} }
if (metaChannel != null) { if (metaChannel != null) {
@ -162,16 +164,16 @@ public class RegistrationRemoteHandlerClientTCP extends RegistrationRemoteHandle
// against that ip-address::key pair, so we can better protect against MITM/spoof attacks. // against that ip-address::key pair, so we can better protect against MITM/spoof attacks.
InetSocketAddress tcpRemoteServer = (InetSocketAddress) channel.remoteAddress(); InetSocketAddress tcpRemoteServer = (InetSocketAddress) channel.remoteAddress();
boolean valid = this.registrationWrapper.validateRemoteServerAddress(tcpRemoteServer, registration.publicKey); boolean valid = registrationWrapper2.validateRemoteServerAddress(tcpRemoteServer, registration.publicKey);
if (!valid) { if (!valid) {
//whoa! abort since something messed up! (log happens inside of validate method) //whoa! abort since something messed up! (log happens inside of validate method)
String hostAddress = tcpRemoteServer.getAddress().getHostAddress(); String hostAddress = tcpRemoteServer.getAddress().getHostAddress();
this.logger.error("Invalid ECC public key for server IP {} during handshake. WARNING. The server has changed!", hostAddress); logger2.error("Invalid ECC public key for server IP {} during handshake. WARNING. The server has changed!", hostAddress);
this.logger.error("Fix by adding the argument -D{} {} when starting the client.", DELETE_IP, hostAddress); logger2.error("Fix by adding the argument -D{} {} when starting the client.", DELETE_IP, hostAddress);
metaChannel.changedRemoteKey = true; metaChannel.changedRemoteKey = true;
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
return; return;
@ -180,12 +182,12 @@ public class RegistrationRemoteHandlerClientTCP extends RegistrationRemoteHandle
// setup crypto state // setup crypto state
IESEngine decrypt = getEccEngine(); IESEngine decrypt = getEccEngine();
byte[] aesKeyBytes = Crypto.ECC.decrypt(decrypt, this.registrationWrapper.getPrivateKey(), registration.publicKey, registration.eccParameters, byte[] aesKeyBytes = Crypto.ECC.decrypt(decrypt, registrationWrapper2.getPrivateKey(), registration.publicKey, registration.eccParameters,
registration.aesKey); registration.aesKey);
if (aesKeyBytes.length != 32) { if (aesKeyBytes.length != 32) {
this.logger.error("Invalid decryption of aesKey. Aborting."); logger2.error("Invalid decryption of aesKey. Aborting.");
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
return; return;
@ -195,8 +197,8 @@ public class RegistrationRemoteHandlerClientTCP extends RegistrationRemoteHandle
byte[] payload = Crypto.AES.decrypt(getAesEngine(), aesKeyBytes, registration.aesIV, registration.payload); byte[] payload = Crypto.AES.decrypt(getAesEngine(), aesKeyBytes, registration.aesIV, registration.payload);
if (payload.length == 0) { if (payload.length == 0) {
this.logger.error("Invalid decryption of payload. Aborting."); logger2.error("Invalid decryption of payload. Aborting.");
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
return; return;
@ -204,8 +206,8 @@ public class RegistrationRemoteHandlerClientTCP extends RegistrationRemoteHandle
OptimizeUtils optimizeUtils = OptimizeUtils.get(); OptimizeUtils optimizeUtils = OptimizeUtils.get();
if (!optimizeUtils.canReadInt(payload)) { if (!optimizeUtils.canReadInt(payload)) {
this.logger.error("Invalid decryption of connection ID. Aborting."); logger2.error("Invalid decryption of connection ID. Aborting.");
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
return; return;
@ -222,8 +224,8 @@ public class RegistrationRemoteHandlerClientTCP extends RegistrationRemoteHandle
ECPublicKeyParameters ecdhPubKey = EccPublicKeySerializer.read(new Input(ecdhPubKeyBytes)); ECPublicKeyParameters ecdhPubKey = EccPublicKeySerializer.read(new Input(ecdhPubKeyBytes));
if (ecdhPubKey == null) { if (ecdhPubKey == null) {
this.logger.error("Invalid decode of ecdh public key. Aborting."); logger2.error("Invalid decode of ecdh public key. Aborting.");
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
return; return;
@ -235,10 +237,10 @@ public class RegistrationRemoteHandlerClientTCP extends RegistrationRemoteHandle
// register the channel! // register the channel!
try { try {
IntMap<MetaChannel> channelMap = this.registrationWrapper.getAndLockChannelMap(); IntMap<MetaChannel> channelMap = registrationWrapper2.getAndLockChannelMap();
channelMap.put(metaChannel.connectionID, metaChannel); channelMap.put(metaChannel.connectionID, metaChannel);
} finally { } finally {
this.registrationWrapper.releaseChannelMap(); registrationWrapper2.releaseChannelMap();
} }
metaChannel.publicKey = registration.publicKey; metaChannel.publicKey = registration.publicKey;
@ -262,8 +264,8 @@ public class RegistrationRemoteHandlerClientTCP extends RegistrationRemoteHandle
// abort if something messed up! // abort if something messed up!
if (metaChannel.aesKey.length != 32) { if (metaChannel.aesKey.length != 32) {
this.logger.error("Fatal error trying to use AES key (wrong key length)."); logger2.error("Fatal error trying to use AES key (wrong key length).");
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
return; return;
@ -294,7 +296,7 @@ public class RegistrationRemoteHandlerClientTCP extends RegistrationRemoteHandle
metaChannel.ecdhKey = null; metaChannel.ecdhKey = null;
// notify the client that we are ready to continue registering other session protocols (bootstraps) // notify the client that we are ready to continue registering other session protocols (bootstraps)
boolean isDoneWithRegistration = this.registrationWrapper.continueRegistration0(); boolean isDoneWithRegistration = registrationWrapper2.continueRegistration0();
// tell the server we are done, and to setup crypto on it's side // tell the server we are done, and to setup crypto on it's side
if (isDoneWithRegistration) { if (isDoneWithRegistration) {
@ -334,8 +336,8 @@ public class RegistrationRemoteHandlerClientTCP extends RegistrationRemoteHandle
} }
} }
else { else {
this.logger.error("Error registering TCP with remote server!"); logger2.error("Error registering TCP with remote server!");
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
} }
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);

View File

@ -69,8 +69,9 @@ public class RegistrationRemoteHandlerClientUDP extends RegistrationRemoteHandle
InetAddress udpRemoteServer = udpRemoteAddress.getAddress(); InetAddress udpRemoteServer = udpRemoteAddress.getAddress();
RegistrationWrapper registrationWrapper2 = this.registrationWrapper;
try { try {
IntMap<MetaChannel> channelMap = this.registrationWrapper.getAndLockChannelMap(); IntMap<MetaChannel> channelMap = registrationWrapper2.getAndLockChannelMap();
Entries<MetaChannel> entries = channelMap.entries(); Entries<MetaChannel> entries = channelMap.entries();
while (entries.hasNext()) { while (entries.hasNext()) {
MetaChannel metaChannel = entries.next().value; MetaChannel metaChannel = entries.next().value;
@ -86,7 +87,7 @@ public class RegistrationRemoteHandlerClientUDP extends RegistrationRemoteHandle
} }
} }
} finally { } finally {
this.registrationWrapper.releaseChannelMap(); registrationWrapper2.releaseChannelMap();
} }
if (!success) { if (!success) {
@ -112,11 +113,12 @@ public class RegistrationRemoteHandlerClientUDP extends RegistrationRemoteHandle
// if we also have a UDP channel, we will receive the "connected" message on UDP (otherwise it will be on TCP) // if we also have a UDP channel, we will receive the "connected" message on UDP (otherwise it will be on TCP)
MetaChannel metaChannel = null; MetaChannel metaChannel = null;
RegistrationWrapper registrationWrapper2 = this.registrationWrapper;
try { try {
IntMap<MetaChannel> channelMap = this.registrationWrapper.getAndLockChannelMap(); IntMap<MetaChannel> channelMap = registrationWrapper2.getAndLockChannelMap();
metaChannel = channelMap.get(channel.hashCode()); metaChannel = channelMap.get(channel.hashCode());
} finally { } finally {
this.registrationWrapper.releaseChannelMap(); registrationWrapper2.releaseChannelMap();
} }
if (metaChannel != null) { if (metaChannel != null) {
@ -129,7 +131,7 @@ public class RegistrationRemoteHandlerClientUDP extends RegistrationRemoteHandle
OptimizeUtils optimizeUtils = OptimizeUtils.get(); OptimizeUtils optimizeUtils = OptimizeUtils.get();
if (!optimizeUtils.canReadInt(payload)) { if (!optimizeUtils.canReadInt(payload)) {
this.logger.error("Invalid decryption of connection ID. Aborting."); this.logger.error("Invalid decryption of connection ID. Aborting.");
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
return; return;
@ -139,17 +141,17 @@ public class RegistrationRemoteHandlerClientUDP extends RegistrationRemoteHandle
MetaChannel metaChannel2 = null; MetaChannel metaChannel2 = null;
try { try {
IntMap<MetaChannel> channelMap = this.registrationWrapper.getAndLockChannelMap(); IntMap<MetaChannel> channelMap = registrationWrapper2.getAndLockChannelMap();
metaChannel2 = channelMap.get(connectionID); metaChannel2 = channelMap.get(connectionID);
} finally { } finally {
this.registrationWrapper.releaseChannelMap(); registrationWrapper2.releaseChannelMap();
} }
if (metaChannel2 != null) { if (metaChannel2 != null) {
// hooray! we are successful // hooray! we are successful
// notify the client that we are ready to continue registering other session protocols (bootstraps) // notify the client that we are ready to continue registering other session protocols (bootstraps)
boolean isDoneWithRegistration = this.registrationWrapper.continueRegistration0(); boolean isDoneWithRegistration = registrationWrapper2.continueRegistration0();
// tell the server we are done, and to setup crypto on it's side // tell the server we are done, and to setup crypto on it's side
if (isDoneWithRegistration) { if (isDoneWithRegistration) {
@ -173,7 +175,7 @@ public class RegistrationRemoteHandlerClientUDP extends RegistrationRemoteHandle
// if we get here, there was an error! // if we get here, there was an error!
this.logger.error("Error registering UDP with remote server!"); this.logger.error("Error registering UDP with remote server!");
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
} }

View File

@ -59,8 +59,9 @@ public class RegistrationRemoteHandlerClientUDT extends RegistrationRemoteHandle
if (udtRemoteAddress != null) { if (udtRemoteAddress != null) {
InetAddress udtRemoteServer = udtRemoteAddress.getAddress(); InetAddress udtRemoteServer = udtRemoteAddress.getAddress();
RegistrationWrapper registrationWrapper2 = this.registrationWrapper;
try { try {
IntMap<MetaChannel> channelMap = this.registrationWrapper.getAndLockChannelMap(); IntMap<MetaChannel> channelMap = registrationWrapper2.getAndLockChannelMap();
Entries<MetaChannel> entries = channelMap.entries(); Entries<MetaChannel> entries = channelMap.entries();
while (entries.hasNext()) { while (entries.hasNext()) {
MetaChannel metaChannel = entries.next().value; MetaChannel metaChannel = entries.next().value;
@ -77,7 +78,7 @@ public class RegistrationRemoteHandlerClientUDT extends RegistrationRemoteHandle
} }
} finally { } finally {
this.registrationWrapper.releaseChannelMap(); registrationWrapper2.releaseChannelMap();
} }
if (!success) { if (!success) {
@ -104,13 +105,15 @@ public class RegistrationRemoteHandlerClientUDT extends RegistrationRemoteHandle
// if we also have a UDP channel, we will receive the "connected" message on UDP (otherwise it will be on TCP) // if we also have a UDP channel, we will receive the "connected" message on UDP (otherwise it will be on TCP)
MetaChannel metaChannel = null; MetaChannel metaChannel = null;
RegistrationWrapper registrationWrapper2 = this.registrationWrapper;
try { try {
IntMap<MetaChannel> channelMap = this.registrationWrapper.getAndLockChannelMap(); IntMap<MetaChannel> channelMap = registrationWrapper2.getAndLockChannelMap();
metaChannel = channelMap.get(channel.hashCode()); metaChannel = channelMap.get(channel.hashCode());
} finally { } finally {
this.registrationWrapper.releaseChannelMap(); registrationWrapper2.releaseChannelMap();
} }
Logger logger2 = this.logger;
if (metaChannel != null) { if (metaChannel != null) {
if (message instanceof Registration) { if (message instanceof Registration) {
Registration registration = (Registration) message; Registration registration = (Registration) message;
@ -120,8 +123,8 @@ public class RegistrationRemoteHandlerClientUDT extends RegistrationRemoteHandle
OptimizeUtils optimizeUtils = OptimizeUtils.get(); OptimizeUtils optimizeUtils = OptimizeUtils.get();
if (!optimizeUtils.canReadInt(payload)) { if (!optimizeUtils.canReadInt(payload)) {
this.logger.error("Invalid decryption of connection ID. Aborting."); logger2.error("Invalid decryption of connection ID. Aborting.");
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
return; return;
@ -131,17 +134,17 @@ public class RegistrationRemoteHandlerClientUDT extends RegistrationRemoteHandle
MetaChannel metaChannel2 = null; MetaChannel metaChannel2 = null;
try { try {
IntMap<MetaChannel> channelMap = this.registrationWrapper.getAndLockChannelMap(); IntMap<MetaChannel> channelMap = registrationWrapper2.getAndLockChannelMap();
metaChannel2 = channelMap.get(connectionID); metaChannel2 = channelMap.get(connectionID);
} finally { } finally {
this.registrationWrapper.releaseChannelMap(); registrationWrapper2.releaseChannelMap();
} }
if (metaChannel2 != null) { if (metaChannel2 != null) {
// hooray! we are successful // hooray! we are successful
// notify the client that we are ready to continue registering other session protocols (bootstraps) // notify the client that we are ready to continue registering other session protocols (bootstraps)
boolean isDoneWithRegistration = this.registrationWrapper.continueRegistration0(); boolean isDoneWithRegistration = registrationWrapper2.continueRegistration0();
// tell the server we are done, and to setup crypto on it's side // tell the server we are done, and to setup crypto on it's side
if (isDoneWithRegistration) { if (isDoneWithRegistration) {
@ -164,8 +167,8 @@ public class RegistrationRemoteHandlerClientUDT extends RegistrationRemoteHandle
// if we get here, there was an error! // if we get here, there was an error!
this.logger.error("Error registering UDT with remote server!"); logger2.error("Error registering UDT with remote server!");
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
} }
} }

View File

@ -117,29 +117,30 @@ public class RegistrationRemoteHandlerServerTCP extends RegistrationRemoteHandle
// only TCP will come across here for the server. (UDP here is called by the UDP handler/wrapper) // only TCP will come across here for the server. (UDP here is called by the UDP handler/wrapper)
RegistrationWrapper registrationWrapper2 = this.registrationWrapper;
if (message instanceof Registration) { if (message instanceof Registration) {
Registration registration = (Registration) message; Registration registration = (Registration) message;
MetaChannel metaChannel = null; MetaChannel metaChannel = null;
try { try {
IntMap<MetaChannel> channelMap = this.registrationWrapper.getAndLockChannelMap(); IntMap<MetaChannel> channelMap = registrationWrapper2.getAndLockChannelMap();
metaChannel = channelMap.get(channel.hashCode()); metaChannel = channelMap.get(channel.hashCode());
} finally { } finally {
this.registrationWrapper.releaseChannelMap(); registrationWrapper2.releaseChannelMap();
} }
// make sure this connection was properly registered in the map. (IT SHOULD BE) // make sure this connection was properly registered in the map. (IT SHOULD BE)
Logger logger2 = this.logger; Logger logger2 = this.logger;
if (metaChannel != null) { if (metaChannel != null) {
metaChannel.updateTcpRoundTripTime(); metaChannel.updateTcpRoundTripTime();
SecureRandom secureRandom = this.registrationWrapper.getSecureRandom(); SecureRandom secureRandom = registrationWrapper2.getSecureRandom();
// first time we've seen data from this new TCP connection // first time we've seen data from this new TCP connection
if (metaChannel.connectionID == null) { if (metaChannel.connectionID == null) {
// whoa! Didn't send valid public key info! // whoa! Didn't send valid public key info!
if (registration.publicKey == null) { if (registration.publicKey == null) {
logger2.error("Null ECC public key during client handshake. This shouldn't happen!"); logger2.error("Null ECC public key during client handshake. This shouldn't happen!");
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
return; return;
@ -149,11 +150,11 @@ public class RegistrationRemoteHandlerServerTCP extends RegistrationRemoteHandle
// against that ip-address::key pair, so we can better protect against MITM/spoof attacks. // against that ip-address::key pair, so we can better protect against MITM/spoof attacks.
InetSocketAddress tcpRemoteClient = (InetSocketAddress) channel.remoteAddress(); InetSocketAddress tcpRemoteClient = (InetSocketAddress) channel.remoteAddress();
boolean valid = this.registrationWrapper.validateRemoteServerAddress(tcpRemoteClient, registration.publicKey); boolean valid = registrationWrapper2.validateRemoteServerAddress(tcpRemoteClient, registration.publicKey);
if (!valid) { if (!valid) {
//whoa! abort since something messed up! (log happens inside of validate method) //whoa! abort since something messed up! (log happens inside of validate method)
if (this.logger.isInfoEnabled()) { if (logger2.isInfoEnabled()) {
logger2.info("Invalid ECC public key for IP {} during handshake with client. Toggling extra flag in channel to indicate this.", tcpRemoteClient.getAddress().getHostAddress()); logger2.info("Invalid ECC public key for IP {} during handshake with client. Toggling extra flag in channel to indicate this.", tcpRemoteClient.getAddress().getHostAddress());
} }
metaChannel.changedRemoteKey = true; metaChannel.changedRemoteKey = true;
@ -164,7 +165,7 @@ public class RegistrationRemoteHandlerServerTCP extends RegistrationRemoteHandle
// if I'm unlucky, keep from confusing connections! // if I'm unlucky, keep from confusing connections!
try { try {
IntMap<MetaChannel> channelMap = this.registrationWrapper.getAndLockChannelMap(); IntMap<MetaChannel> channelMap = registrationWrapper2.getAndLockChannelMap();
while (channelMap.containsKey(connectionID)) { while (channelMap.containsKey(connectionID)) {
connectionID = MathUtils.randomInt(); connectionID = MathUtils.randomInt();
} }
@ -173,7 +174,7 @@ public class RegistrationRemoteHandlerServerTCP extends RegistrationRemoteHandle
channelMap.put(connectionID, metaChannel); channelMap.put(connectionID, metaChannel);
} finally { } finally {
this.registrationWrapper.releaseChannelMap(); registrationWrapper2.releaseChannelMap();
} }
Registration register = new Registration(); Registration register = new Registration();
@ -214,13 +215,13 @@ public class RegistrationRemoteHandlerServerTCP extends RegistrationRemoteHandle
IESEngine encrypt = getEccEngine(); IESEngine encrypt = getEccEngine();
register.publicKey = this.registrationWrapper.getPublicKey(); register.publicKey = registrationWrapper2.getPublicKey();
register.eccParameters = Crypto.ECC.generateSharedParameters(secureRandom); register.eccParameters = Crypto.ECC.generateSharedParameters(secureRandom);
// now we have to ENCRYPT the AES key! // now we have to ENCRYPT the AES key!
register.eccParameters = Crypto.ECC.generateSharedParameters(secureRandom); register.eccParameters = Crypto.ECC.generateSharedParameters(secureRandom);
register.aesIV = metaChannel.aesIV; register.aesIV = metaChannel.aesIV;
register.aesKey = Crypto.ECC.encrypt(encrypt, this.registrationWrapper.getPrivateKey(), metaChannel.publicKey, register.eccParameters, metaChannel.aesKey); register.aesKey = Crypto.ECC.encrypt(encrypt, registrationWrapper2.getPrivateKey(), metaChannel.publicKey, register.eccParameters, metaChannel.aesKey);
// now encrypt payload via AES // now encrypt payload via AES
@ -251,7 +252,7 @@ public class RegistrationRemoteHandlerServerTCP extends RegistrationRemoteHandle
if (payload.length == 0) { if (payload.length == 0) {
logger2.error("Invalid decryption of payload. Aborting."); logger2.error("Invalid decryption of payload. Aborting.");
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
return; return;
@ -261,7 +262,7 @@ public class RegistrationRemoteHandlerServerTCP extends RegistrationRemoteHandle
if (ecdhPubKey == null) { if (ecdhPubKey == null) {
logger2.error("Invalid decode of ecdh public key. Aborting."); logger2.error("Invalid decode of ecdh public key. Aborting.");
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
return; return;
@ -325,7 +326,7 @@ public class RegistrationRemoteHandlerServerTCP extends RegistrationRemoteHandle
logger2.error("Error registering TCP channel! MetaChannel is null!"); logger2.error("Error registering TCP channel! MetaChannel is null!");
} }
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
} }
} }

View File

@ -138,19 +138,22 @@ public class RegistrationRemoteHandlerServerUDP extends MessageToMessageCodec<Da
public final void receivedUDP(ChannelHandlerContext context, Channel channel, ByteBuf data, InetSocketAddress udpRemoteAddress) throws Exception { public final void receivedUDP(ChannelHandlerContext context, Channel channel, ByteBuf data, InetSocketAddress udpRemoteAddress) throws Exception {
// registration is the ONLY thing NOT encrypted // registration is the ONLY thing NOT encrypted
Logger logger2 = this.logger; Logger logger2 = this.logger;
if (this.serializationManager.isEncrypted(data)) { RegistrationWrapper registrationWrapper2 = this.registrationWrapper;
SerializationManager serializationManager2 = this.serializationManager;
if (serializationManager2.isEncrypted(data)) {
// we need to FORWARD this message "down the pipeline". // we need to FORWARD this message "down the pipeline".
ConnectionImpl connection = this.registrationWrapper.getServerUDP(udpRemoteAddress); ConnectionImpl connection = registrationWrapper2.getServerUDP(udpRemoteAddress);
if (connection != null) { if (connection != null) {
// try to read data! (IT SHOULD ALWAYS BE ENCRYPTED HERE!) // try to read data! (IT SHOULD ALWAYS BE ENCRYPTED HERE!)
Object object; Object object;
try { try {
object = this.serializationManager.readWithCryptoUdp(connection, data, data.writerIndex()); object = serializationManager2.readWithCryptoUdp(connection, data, data.writerIndex());
} catch (NetException e) { } catch (NetException e) {
logger2.error("UDP unable to deserialize buffer", e); logger2.error("UDP unable to deserialize buffer", e);
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
return; return;
} }
@ -167,10 +170,10 @@ public class RegistrationRemoteHandlerServerUDP extends MessageToMessageCodec<Da
Object object; Object object;
try { try {
object = this.serializationManager.read(data, data.writerIndex()); object = serializationManager2.read(data, data.writerIndex());
} catch (NetException e) { } catch (NetException e) {
logger2.error("UDP unable to deserialize buffer", e); logger2.error("UDP unable to deserialize buffer", e);
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
return; return;
} }
@ -181,7 +184,7 @@ public class RegistrationRemoteHandlerServerUDP extends MessageToMessageCodec<Da
try { try {
// find out and make sure that UDP and TCP are talking to the same server // find out and make sure that UDP and TCP are talking to the same server
InetAddress udpRemoteServer = udpRemoteAddress.getAddress(); InetAddress udpRemoteServer = udpRemoteAddress.getAddress();
IntMap<MetaChannel> channelMap = this.registrationWrapper.getAndLockChannelMap(); IntMap<MetaChannel> channelMap = registrationWrapper2.getAndLockChannelMap();
Entries<MetaChannel> entries = channelMap.entries(); Entries<MetaChannel> entries = channelMap.entries();
while (entries.hasNext()) { while (entries.hasNext()) {
@ -197,13 +200,13 @@ public class RegistrationRemoteHandlerServerUDP extends MessageToMessageCodec<Da
break; break;
} else { } else {
logger2.error("Mismatch UDP and TCP client addresses! UDP: {} TCP: {}", udpRemoteServer, tcpRemoteAddress); logger2.error("Mismatch UDP and TCP client addresses! UDP: {} TCP: {}", udpRemoteServer, tcpRemoteAddress);
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
return; return;
} }
} }
} }
} finally { } finally {
this.registrationWrapper.releaseChannelMap(); registrationWrapper2.releaseChannelMap();
} }
@ -233,7 +236,7 @@ public class RegistrationRemoteHandlerServerUDP extends MessageToMessageCodec<Da
// if we get here, there was a failure! // if we get here, there was a failure!
logger2.error("Error trying to register UDP without udp specified! UDP: {}", udpRemoteAddress); logger2.error("Error trying to register UDP without udp specified! UDP: {}", udpRemoteAddress);
shutdown(this.registrationWrapper, channel); shutdown(registrationWrapper2, channel);
return; return;
} }
else { else {

View File

@ -7,6 +7,8 @@ import io.netty.util.ReferenceCountUtil;
import java.net.InetAddress; import java.net.InetAddress;
import java.net.InetSocketAddress; import java.net.InetSocketAddress;
import org.slf4j.Logger;
import dorkbox.network.connection.RegistrationWrapper; import dorkbox.network.connection.RegistrationWrapper;
import dorkbox.network.connection.registration.MetaChannel; import dorkbox.network.connection.registration.MetaChannel;
import dorkbox.network.connection.registration.Registration; import dorkbox.network.connection.registration.Registration;
@ -35,7 +37,7 @@ public class RegistrationRemoteHandlerServerUDT extends RegistrationRemoteHandle
*/ */
@Override @Override
public void channelActive(ChannelHandlerContext context) throws Exception { public void channelActive(ChannelHandlerContext context) throws Exception {
if (logger.isDebugEnabled()) { if (this.logger.isDebugEnabled()) {
super.channelActive(context); super.channelActive(context);
} }
@ -51,6 +53,9 @@ public class RegistrationRemoteHandlerServerUDT extends RegistrationRemoteHandle
// only TCP will come across here for the server. (UDP here is called by the UDP handler/wrapper) // only TCP will come across here for the server. (UDP here is called by the UDP handler/wrapper)
RegistrationWrapper registrationWrapper2 = this.registrationWrapper;
Logger logger2 = this.logger;
if (message instanceof Registration) { if (message instanceof Registration) {
// find out and make sure that UDP and TCP are talking to the same server // find out and make sure that UDP and TCP are talking to the same server
InetAddress udtRemoteAddress = ((InetSocketAddress) channel.remoteAddress()).getAddress(); InetAddress udtRemoteAddress = ((InetSocketAddress) channel.remoteAddress()).getAddress();
@ -58,7 +63,7 @@ public class RegistrationRemoteHandlerServerUDT extends RegistrationRemoteHandle
boolean matches = false; boolean matches = false;
MetaChannel metaChannel = null; MetaChannel metaChannel = null;
try { try {
IntMap<MetaChannel> channelMap = registrationWrapper.getAndLockChannelMap(); IntMap<MetaChannel> channelMap = registrationWrapper2.getAndLockChannelMap();
Entries<MetaChannel> entries = channelMap.entries(); Entries<MetaChannel> entries = channelMap.entries();
while (entries.hasNext()) { while (entries.hasNext()) {
metaChannel = entries.next().value; metaChannel = entries.next().value;
@ -71,8 +76,10 @@ public class RegistrationRemoteHandlerServerUDT extends RegistrationRemoteHandle
if (checkEqual(tcpRemoteAddress, udtRemoteAddress)) { if (checkEqual(tcpRemoteAddress, udtRemoteAddress)) {
matches = true; matches = true;
} else { } else {
logger.error(name, "Mismatch UDT and TCP client addresses! UDP: {} TCP: {}", udtRemoteAddress, tcpRemoteAddress); if (logger2.isErrorEnabled()) {
shutdown(registrationWrapper, channel); logger2.error(this.name, "Mismatch UDT and TCP client addresses! UDP: {} TCP: {}", udtRemoteAddress, tcpRemoteAddress);
}
shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
return; return;
} }
@ -80,7 +87,7 @@ public class RegistrationRemoteHandlerServerUDT extends RegistrationRemoteHandle
} }
} finally { } finally {
registrationWrapper.releaseChannelMap(); registrationWrapper2.releaseChannelMap();
} }
if (matches && metaChannel != null) { if (matches && metaChannel != null) {
@ -104,20 +111,26 @@ public class RegistrationRemoteHandlerServerUDT extends RegistrationRemoteHandle
// since we are done here, we need to REMOVE this handler // since we are done here, we need to REMOVE this handler
channel.pipeline().remove(this); channel.pipeline().remove(this);
logger.trace("Register UDT connection from {}", udtRemoteAddress); if (logger2.isTraceEnabled()) {
logger2.trace("Register UDT connection from {}", udtRemoteAddress);
}
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
return; return;
} }
// if we get here, there was a failure! // if we get here, there was a failure!
logger.error("Error trying to register UDT without udt specified! UDT: {}", udtRemoteAddress); if (logger2.isErrorEnabled()) {
shutdown(registrationWrapper, channel); logger2.error("Error trying to register UDT without udt specified! UDT: {}", udtRemoteAddress);
}
shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
return; return;
} }
else { else {
logger.error("UDT attempting to spoof client! Unencrypted packet other than registration received."); if (logger2.isErrorEnabled()) {
shutdown(registrationWrapper, channel); logger2.error("UDT attempting to spoof client! Unencrypted packet other than registration received.");
}
shutdown(registrationWrapper2, channel);
ReferenceCountUtil.release(message); ReferenceCountUtil.release(message);
return; return;
} }