restructure packet handlers

This commit is contained in:
sirjonasxx 2018-10-03 00:22:36 +02:00
parent 5ece05b4b1
commit e110a34118
4 changed files with 104 additions and 153 deletions

View File

@ -35,10 +35,13 @@ public class Rc4Obtainer {
} }
}); });
} }
public void setIncomingHandler(IncomingHandler handler) { public void setIncomingHandler(IncomingHandler handler) {
incomingHandler = handler; incomingHandler = handler;
} }
private void onSendFirstEncryptedMessage() { private void onSendFirstEncryptedMessage() {
outgoingHandler.block(); outgoingHandler.block();
incomingHandler.block(); incomingHandler.block();

View File

@ -1,6 +1,7 @@
package main.protocol.packethandler; package main.protocol.packethandler;
import main.protocol.HMessage; import main.protocol.HMessage;
import main.protocol.HPacket;
import main.protocol.TrafficListener; import main.protocol.TrafficListener;
import main.protocol.crypto.RC4; import main.protocol.crypto.RC4;
@ -20,8 +21,13 @@ public abstract class Handler {
volatile boolean isDataStream = false; volatile boolean isDataStream = false;
volatile int currentIndex = 0; volatile int currentIndex = 0;
protected RC4 clientcipher = null; protected final Object lock = new Object();
protected RC4 servercipher = null;
protected RC4 decryptcipher = null;
protected RC4 encryptcipher = null;
protected volatile List<Byte> tempEncryptedBuffer = new ArrayList<>();
protected volatile boolean isEncryptedStream = false;
public Handler(OutputStream outputStream, Object[] listeners) { public Handler(OutputStream outputStream, Object[] listeners) {
@ -35,10 +41,46 @@ public abstract class Handler {
} }
public abstract void act(byte[] buffer) throws IOException; public abstract void act(byte[] buffer) throws IOException;
protected void continuedAct(byte[] buffer) throws IOException {
if (!isEncryptedStream) {
payloadBuffer.push(buffer);
}
else if (decryptcipher == null) {
for (int i = 0; i < buffer.length; i++) {
tempEncryptedBuffer.add(buffer[i]);
}
}
else {
byte[] tm = decryptcipher.rc4(buffer);
if (DEBUG) {
printForDebugging(tm);
}
payloadBuffer.push(tm);
}
notifyBufferListeners(buffer.length);
if (!isTempBlocked) {
flush();
}
}
public void setRc4(RC4 rc4) { public void setRc4(RC4 rc4) {
this.clientcipher = rc4.deepCopy(); this.decryptcipher = rc4.deepCopy();
this.servercipher = rc4.deepCopy(); this.encryptcipher = rc4.deepCopy();
byte[] encrbuffer = new byte[tempEncryptedBuffer.size()];
for (int i = 0; i < tempEncryptedBuffer.size(); i++) {
encrbuffer[i] = tempEncryptedBuffer.get(i);
}
try {
act(encrbuffer);
} catch (IOException e) {
e.printStackTrace();
}
tempEncryptedBuffer = null;
} }
public void block() { public void block() {
@ -68,9 +110,47 @@ public abstract class Handler {
listener.onCapture(message); listener.onCapture(message);
} }
} }
public abstract void sendToStream(byte[] buffer);
public abstract void flush() throws IOException; public void sendToStream(byte[] buffer) {
synchronized (lock) {
try {
out.write(
(!isEncryptedStream)
? buffer
: encryptcipher.rc4(buffer)
);
} catch (IOException e) {
e.printStackTrace();
}
}
}
public void flush() throws IOException {
synchronized (lock) {
HPacket[] hpackets = payloadBuffer.receive();
for (HPacket hpacket : hpackets){
HMessage hMessage = new HMessage(hpacket, HMessage.Side.TOCLIENT, currentIndex);
boolean isencrypted = isEncryptedStream;
if (isDataStream) {
notifyListeners(hMessage);
}
if (!hMessage.isBlocked()) {
out.write(
(!isencrypted)
? hMessage.getPacket().toBytes()
: encryptcipher.rc4(hMessage.getPacket().toBytes())
);
}
currentIndex++;
}
}
}
public List<Byte> getEncryptedBuffer() {
return tempEncryptedBuffer;
}
protected abstract void printForDebugging(byte[] bytes); protected abstract void printForDebugging(byte[] bytes);

View File

@ -2,93 +2,36 @@ package main.protocol.packethandler;
import main.protocol.HMessage; import main.protocol.HMessage;
import main.protocol.HPacket; import main.protocol.HPacket;
import main.protocol.memory.Rc4Obtainer; import main.protocol.TrafficListener;
import java.io.IOException; import java.io.IOException;
import java.io.OutputStream; import java.io.OutputStream;
import java.util.List;
public class IncomingHandler extends Handler { public class IncomingHandler extends Handler {
private volatile boolean onlyOnce = true;
public IncomingHandler(OutputStream outputStream, Object[] listeners) { public IncomingHandler(OutputStream outputStream, Object[] listeners) {
super(outputStream, listeners); super(outputStream, listeners);
((List<TrafficListener>)listeners[0]).add(message -> {
if (isDataStream && onlyOnce && message.getPacket().length() == 261) {
onlyOnce = false;
isEncryptedStream = message.getPacket().readBoolean(264);
}
});
} }
private final Object lock = new Object();
private Boolean isEncryptedStream = null;
@Override @Override
public void act(byte[] buffer) throws IOException { public void act(byte[] buffer) throws IOException {
if (isDataStream) { if (isDataStream) {
if (DEBUG) { continuedAct(buffer);
printForDebugging(buffer);
}
if (isEncryptedStream == null || !isEncryptedStream) {
payloadBuffer.push(buffer);
}
else {
payloadBuffer.push(servercipher.rc4(buffer));
}
notifyBufferListeners(buffer.length);
if (!isTempBlocked) {
flush();
}
} }
else { else {
out.write(buffer); out.write(buffer);
} }
} }
@Override
public void sendToStream(byte[] buffer) {
synchronized (lock) {
try {
out.write(
(isEncryptedStream == null || !isEncryptedStream)
? buffer
: clientcipher.rc4(buffer)
);
} catch (IOException e) {
e.printStackTrace();
}
}
}
@Override
public void flush() throws IOException {
synchronized (lock) {
HPacket[] hpackets = payloadBuffer.receive();
for (HPacket hpacket : hpackets){
HMessage hMessage = new HMessage(hpacket, HMessage.Side.TOCLIENT, currentIndex);
if (isDataStream) {
notifyListeners(hMessage);
}
if (!hMessage.isBlocked()) {
out.write(
(isEncryptedStream == null || !isEncryptedStream)
? hMessage.getPacket().toBytes()
: clientcipher.rc4(hMessage.getPacket().toBytes())
);
}
if (isDataStream && isEncryptedStream == null && hpacket.length() == 261) {
isEncryptedStream = hpacket.readBoolean(264);
}
currentIndex++;
}
}
}
@Override @Override
protected void printForDebugging(byte[] bytes) { protected void printForDebugging(byte[] bytes) {
System.out.println("-- DEBUG INCOMING -- " + new HPacket(bytes).toString() + " -- DEBUG --"); System.out.println("-- DEBUG INCOMING -- " + new HPacket(bytes).toString() + " -- DEBUG --");

View File

@ -2,21 +2,13 @@ package main.protocol.packethandler;
import main.protocol.HMessage; import main.protocol.HMessage;
import main.protocol.HPacket; import main.protocol.HPacket;
import main.protocol.crypto.RC4;
import main.protocol.memory.Rc4Obtainer;
import java.io.IOException; import java.io.IOException;
import java.io.OutputStream; import java.io.OutputStream;
import java.util.ArrayList;
import java.util.List; import java.util.List;
public class OutgoingHandler extends Handler { public class OutgoingHandler extends Handler {
private final Object lock = new Object();
private final static int encryptOffset = 3; //all packets with index < 3 aren't encrypted
private List<Byte> tempEncryptedBuffer = new ArrayList<>();
public OutgoingHandler(OutputStream outputStream, Object[] listeners) { public OutgoingHandler(OutputStream outputStream, Object[] listeners) {
super(outputStream, listeners); super(outputStream, listeners);
} }
@ -31,86 +23,19 @@ public class OutgoingHandler extends Handler {
@Override @Override
public void act(byte[] buffer) throws IOException { public void act(byte[] buffer) throws IOException {
dataStreamCheck(buffer); dataStreamCheck(buffer);
if (isDataStream) { if (isDataStream) {
if (currentIndex < encryptOffset) { if (!isEncryptedStream && (new HPacket(buffer).length() < 2 || new HPacket(buffer).length() > 1000)) {
payloadBuffer.push(buffer); isEncryptedStream = true;
}
else if (clientcipher == null) {
for (int i = 0; i < buffer.length; i++) {
tempEncryptedBuffer.add(buffer[i]);
}
}
else {
byte[] tm = clientcipher.rc4(buffer);
if (DEBUG) {
printForDebugging(tm);
}
payloadBuffer.push(tm);
} }
notifyBufferListeners(buffer.length); continuedAct(buffer);
if (!isTempBlocked) {
flush();
}
} }
else { else {
out.write(buffer); out.write(buffer);
} }
} }
@Override
public void setRc4(RC4 rc4) {
super.setRc4(rc4);
byte[] encrbuffer = new byte[tempEncryptedBuffer.size()];
for (int i = 0; i < tempEncryptedBuffer.size(); i++) {
encrbuffer[i] = tempEncryptedBuffer.get(i);
}
try {
act(encrbuffer);
} catch (IOException e) {
e.printStackTrace();
}
tempEncryptedBuffer = null;
}
@Override
public void sendToStream(byte[] buffer) {
synchronized (lock) {
try {
out.write(servercipher.rc4(buffer));
} catch (IOException e) {
e.printStackTrace();
}
}
}
public List<Byte> getEncryptedBuffer() {
return tempEncryptedBuffer;
}
@Override
public void flush() throws IOException {
synchronized (lock) {
HPacket[] hpackets = payloadBuffer.receive();
for (HPacket hpacket : hpackets){
HMessage hMessage = new HMessage(hpacket, HMessage.Side.TOSERVER, currentIndex);
if (isDataStream) notifyListeners(hMessage);
if (!hMessage.isBlocked()) {
out.write(
currentIndex < encryptOffset ? hMessage.getPacket().toBytes() :
servercipher.rc4(hMessage.getPacket().toBytes())
);
}
currentIndex ++;
}
}
}
@Override @Override
protected void printForDebugging(byte[] bytes) { protected void printForDebugging(byte[] bytes) {