use of org.apollo.util.security.PlayerCredentials in project apollo by apollo-rsps.
the class LoginDecoder method decodePayload.
/**
* Decodes in the payload state.
*
* @param ctx The channel handler context.
* @param buffer The buffer.
* @param out The {@link List} of objects to pass forward through the pipeline.
*/
private void decodePayload(ChannelHandlerContext ctx, ByteBuf buffer, List<Object> out) {
if (buffer.readableBytes() >= loginLength) {
ByteBuf payload = buffer.readBytes(loginLength);
int version = 255 - payload.readUnsignedByte();
int release = payload.readUnsignedShort();
int memoryStatus = payload.readUnsignedByte();
if (memoryStatus != 0 && memoryStatus != 1) {
logger.fine("Login memoryStatus (" + memoryStatus + ") not in expected range of [0, 1].");
writeResponseCode(ctx, LoginConstants.STATUS_LOGIN_SERVER_REJECTED_SESSION);
return;
}
boolean lowMemory = memoryStatus == 1;
int[] crcs = new int[FileSystemConstants.ARCHIVE_COUNT];
for (int index = 0; index < 9; index++) {
crcs[index] = payload.readInt();
}
int length = payload.readUnsignedByte();
if (length != loginLength - 41) {
logger.fine("Login packet unexpected length (" + length + ")");
writeResponseCode(ctx, LoginConstants.STATUS_LOGIN_SERVER_REJECTED_SESSION);
return;
}
ByteBuf secure = payload.readBytes(length);
BigInteger value = new BigInteger(secure.array());
value = value.modPow(NetworkConstants.RSA_EXPONENT, NetworkConstants.RSA_MODULUS);
secure = Unpooled.wrappedBuffer(value.toByteArray());
int id = secure.readUnsignedByte();
if (id != 10) {
logger.fine("Unable to read id from secure payload.");
writeResponseCode(ctx, LoginConstants.STATUS_LOGIN_SERVER_REJECTED_SESSION);
return;
}
long clientSeed = secure.readLong();
long reportedSeed = secure.readLong();
if (reportedSeed != serverSeed) {
logger.fine("Reported seed differed from server seed.");
writeResponseCode(ctx, LoginConstants.STATUS_LOGIN_SERVER_REJECTED_SESSION);
return;
}
int uid = secure.readInt();
String username = BufferUtil.readString(secure);
String password = BufferUtil.readString(secure);
InetSocketAddress socketAddress = (InetSocketAddress) ctx.channel().remoteAddress();
String hostAddress = InetAddresses.toAddrString(socketAddress.getAddress());
if (password.length() < 6 || password.length() > 20 || username.isEmpty() || username.length() > 12) {
logger.fine("Username ('" + username + "') or password did not pass validation.");
writeResponseCode(ctx, LoginConstants.STATUS_INVALID_CREDENTIALS);
return;
}
int[] seed = new int[4];
seed[0] = (int) (clientSeed >> 32);
seed[1] = (int) clientSeed;
seed[2] = (int) (serverSeed >> 32);
seed[3] = (int) serverSeed;
IsaacRandom decodingRandom = new IsaacRandom(seed);
for (int index = 0; index < seed.length; index++) {
seed[index] += 50;
}
IsaacRandom encodingRandom = new IsaacRandom(seed);
PlayerCredentials credentials = new PlayerCredentials(username, password, usernameHash, uid, hostAddress);
IsaacRandomPair randomPair = new IsaacRandomPair(encodingRandom, decodingRandom);
out.add(new LoginRequest(credentials, randomPair, reconnecting, lowMemory, release, crcs, version));
}
}
Aggregations