mirror of
https://github.com/sirjonasxx/G-Earth.git
synced 2024-11-23 08:50:52 +01:00
integrate chrome extension with g-earth
This commit is contained in:
parent
118e7587ac
commit
3e111d3ccc
@ -12,6 +12,7 @@
|
||||
|
||||
<properties>
|
||||
<javafx.version>1.8</javafx.version>
|
||||
<jettyVersion>9.2.14.v20151106</jettyVersion>
|
||||
</properties>
|
||||
|
||||
<parent>
|
||||
@ -123,6 +124,7 @@
|
||||
</plugins>
|
||||
</build>
|
||||
|
||||
|
||||
<dependencies>
|
||||
<!-- <dependency>-->
|
||||
<!-- <groupId>org.openjfx</groupId>-->
|
||||
@ -172,6 +174,24 @@
|
||||
</dependency>
|
||||
|
||||
|
||||
<dependency>
|
||||
<groupId>javax.websocket</groupId>
|
||||
<artifactId>javax.websocket-api</artifactId>
|
||||
<version>1.1</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.eclipse.jetty</groupId>
|
||||
<artifactId>jetty-server</artifactId>
|
||||
<version>${jettyVersion}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.eclipse.jetty.websocket</groupId>
|
||||
<artifactId>javax-websocket-server-impl</artifactId>
|
||||
<version>${jettyVersion}</version>
|
||||
</dependency>
|
||||
|
||||
|
||||
</dependencies>
|
||||
|
||||
<repositories>
|
||||
|
@ -7,6 +7,7 @@ import gearth.protocol.connection.proxy.ProxyProvider;
|
||||
import gearth.protocol.connection.proxy.flash.FlashProxyProvider;
|
||||
import gearth.protocol.connection.proxy.ProxyProviderFactory;
|
||||
import gearth.protocol.connection.proxy.flash.unix.LinuxRawIpFlashProxyProvider;
|
||||
import gearth.protocol.connection.proxy.unity.UnityProxyProvider;
|
||||
import gearth.services.extensionhandler.ExtensionHandler;
|
||||
|
||||
import java.io.IOException;
|
||||
@ -60,6 +61,12 @@ public class HConnection {
|
||||
startMITM();
|
||||
}
|
||||
|
||||
public void startUnity() {
|
||||
HConnection selff = this;
|
||||
proxyProvider = new UnityProxyProvider(proxy -> selff.proxy = proxy, selff::setState, this);
|
||||
startMITM();
|
||||
}
|
||||
|
||||
private void startMITM() {
|
||||
try {
|
||||
if (proxyProvider != null) {
|
||||
|
@ -1,7 +1,8 @@
|
||||
package gearth.protocol.connection;
|
||||
|
||||
import gearth.protocol.packethandler.IncomingPacketHandler;
|
||||
import gearth.protocol.packethandler.OutgoingPacketHandler;
|
||||
import gearth.protocol.packethandler.PacketHandler;
|
||||
import gearth.protocol.packethandler.flash.IncomingFlashPacketHandler;
|
||||
import gearth.protocol.packethandler.flash.OutgoingFlashPacketHandler;
|
||||
|
||||
import java.net.ServerSocket;
|
||||
|
||||
@ -15,8 +16,8 @@ public class HProxy {
|
||||
|
||||
private volatile ServerSocket proxy_server = null; //listener for the client
|
||||
|
||||
private volatile IncomingPacketHandler inHandler = null; //connection with client (only initialized when verified habbo connection)
|
||||
private volatile OutgoingPacketHandler outHandler = null; //connection with server (only initialized when verified habbo connection)
|
||||
private volatile PacketHandler inHandler = null; //connection with client (only initialized when verified habbo connection)
|
||||
private volatile PacketHandler outHandler = null; //connection with server (only initialized when verified habbo connection)
|
||||
|
||||
private volatile String hotelVersion = "";
|
||||
private volatile AsyncPacketSender asyncPacketSender = null;
|
||||
@ -33,7 +34,7 @@ public class HProxy {
|
||||
this.proxy_server = socket;
|
||||
}
|
||||
|
||||
public void verifyProxy(IncomingPacketHandler incomingHandler, OutgoingPacketHandler outgoingHandler, String hotelVersion) {
|
||||
public void verifyProxy(PacketHandler incomingHandler, PacketHandler outgoingHandler, String hotelVersion) {
|
||||
this.inHandler = incomingHandler;
|
||||
this.outHandler = outgoingHandler;
|
||||
this.hotelVersion = hotelVersion;
|
||||
@ -64,11 +65,11 @@ public class HProxy {
|
||||
return intercept_host;
|
||||
}
|
||||
|
||||
public IncomingPacketHandler getInHandler() {
|
||||
public PacketHandler getInHandler() {
|
||||
return inHandler;
|
||||
}
|
||||
|
||||
public OutgoingPacketHandler getOutHandler() {
|
||||
public PacketHandler getOutHandler() {
|
||||
return outHandler;
|
||||
}
|
||||
|
||||
|
@ -7,9 +7,9 @@ import gearth.protocol.connection.HState;
|
||||
import gearth.protocol.connection.HStateSetter;
|
||||
import gearth.protocol.connection.proxy.ProxyProvider;
|
||||
import gearth.protocol.memory.Rc4Obtainer;
|
||||
import gearth.protocol.packethandler.IncomingPacketHandler;
|
||||
import gearth.protocol.packethandler.OutgoingPacketHandler;
|
||||
import gearth.protocol.packethandler.PacketHandler;
|
||||
import gearth.protocol.packethandler.flash.IncomingFlashPacketHandler;
|
||||
import gearth.protocol.packethandler.flash.OutgoingFlashPacketHandler;
|
||||
import gearth.protocol.packethandler.flash.FlashPacketHandler;
|
||||
import javafx.application.Platform;
|
||||
import javafx.scene.control.Alert;
|
||||
import javafx.scene.control.ButtonType;
|
||||
@ -45,9 +45,9 @@ public abstract class FlashProxyProvider implements ProxyProvider {
|
||||
if (HConnection.DEBUG) System.out.println(server.getLocalAddress().getHostAddress() + ": " + server.getLocalPort());
|
||||
Rc4Obtainer rc4Obtainer = new Rc4Obtainer(hConnection);
|
||||
|
||||
OutgoingPacketHandler outgoingHandler = new OutgoingPacketHandler(server.getOutputStream(), hConnection.getTrafficObservables(), hConnection.getExtensionHandler());
|
||||
IncomingPacketHandler incomingHandler = new IncomingPacketHandler(client.getOutputStream(), hConnection.getTrafficObservables(), outgoingHandler, hConnection.getExtensionHandler());
|
||||
rc4Obtainer.setPacketHandlers(outgoingHandler, incomingHandler);
|
||||
OutgoingFlashPacketHandler outgoingHandler = new OutgoingFlashPacketHandler(server.getOutputStream(), hConnection.getTrafficObservables(), hConnection.getExtensionHandler());
|
||||
IncomingFlashPacketHandler incomingHandler = new IncomingFlashPacketHandler(client.getOutputStream(), hConnection.getTrafficObservables(), outgoingHandler, hConnection.getExtensionHandler());
|
||||
rc4Obtainer.setFlashPacketHandlers(outgoingHandler, incomingHandler);
|
||||
|
||||
Semaphore abort = new Semaphore(0);
|
||||
|
||||
@ -78,7 +78,7 @@ public abstract class FlashProxyProvider implements ProxyProvider {
|
||||
}
|
||||
}
|
||||
|
||||
private void handleInputStream(Socket socket, PacketHandler packetHandler, Semaphore abort) {
|
||||
private void handleInputStream(Socket socket, FlashPacketHandler flashPacketHandler, Semaphore abort) {
|
||||
new Thread(() -> {
|
||||
try {
|
||||
int readLength;
|
||||
@ -86,7 +86,7 @@ public abstract class FlashProxyProvider implements ProxyProvider {
|
||||
while (!socket.isClosed() &&
|
||||
(hConnection.getState() == HState.WAITING_FOR_CLIENT || hConnection.getState() == HState.CONNECTED) &&
|
||||
(readLength = socket.getInputStream().read(buffer)) != -1) {
|
||||
packetHandler.act(Arrays.copyOf(buffer, readLength));
|
||||
flashPacketHandler.act(Arrays.copyOf(buffer, readLength));
|
||||
}
|
||||
}
|
||||
catch (IOException ignore) {
|
||||
|
@ -1,4 +0,0 @@
|
||||
package gearth.protocol.connection.proxy.unity;
|
||||
|
||||
public class ProxyProvider {
|
||||
}
|
@ -0,0 +1,86 @@
|
||||
package gearth.protocol.connection.proxy.unity;
|
||||
|
||||
import gearth.protocol.HConnection;
|
||||
import gearth.protocol.HMessage;
|
||||
import gearth.protocol.HPacket;
|
||||
import gearth.protocol.connection.HProxy;
|
||||
import gearth.protocol.connection.HProxySetter;
|
||||
import gearth.protocol.connection.HState;
|
||||
import gearth.protocol.connection.HStateSetter;
|
||||
import gearth.protocol.connection.proxy.ProxyProvider;
|
||||
import gearth.protocol.packethandler.unity.UnityPacketHandler;
|
||||
|
||||
import javax.websocket.*;
|
||||
import javax.websocket.server.ServerEndpoint;
|
||||
import java.io.IOException;
|
||||
import java.nio.ByteBuffer;
|
||||
import java.util.Arrays;
|
||||
|
||||
@ServerEndpoint(value = "/packethandler")
|
||||
public class UnityCommunicator {
|
||||
|
||||
private final HProxySetter proxySetter;
|
||||
private final HStateSetter stateSetter;
|
||||
private final HConnection hConnection;
|
||||
private final ProxyProvider proxyProvider;
|
||||
|
||||
HProxy hProxy = null;
|
||||
|
||||
public UnityCommunicator(HProxySetter proxySetter, HStateSetter stateSetter, HConnection hConnection, ProxyProvider proxyProvider) {
|
||||
this.proxySetter = proxySetter;
|
||||
this.stateSetter = stateSetter;
|
||||
this.hConnection = hConnection;
|
||||
this.proxyProvider = proxyProvider;
|
||||
}
|
||||
|
||||
|
||||
@OnOpen
|
||||
public void onOpen(Session session) throws IOException {
|
||||
|
||||
}
|
||||
|
||||
@OnMessage
|
||||
public void onMessage(byte[] b, Session session) throws IOException {
|
||||
// session.getBasicRemote().sendText(message.toUpperCase());
|
||||
// session.getBasicRemote().sendBinary(ByteBuffer.wrap(b));
|
||||
// System.out.println("received " + new HPacket(b).toString());
|
||||
|
||||
byte[] packet = Arrays.copyOfRange(b, 1, b.length);
|
||||
|
||||
if (hProxy == null && b[0] == 1) {
|
||||
HPacket maybe = new HPacket(packet);
|
||||
if (maybe.getBytesLength() > 6 && maybe.headerId() == 4000) {
|
||||
String hotelVersion = maybe.readString();
|
||||
hProxy = new HProxy("", "", -1, -1, "");
|
||||
hProxy.verifyProxy(
|
||||
new UnityPacketHandler(hConnection.getExtensionHandler(), hConnection.getTrafficObservables(), session, HMessage.Direction.TOCLIENT),
|
||||
new UnityPacketHandler(hConnection.getExtensionHandler(), hConnection.getTrafficObservables(), session, HMessage.Direction.TOSERVER),
|
||||
hotelVersion
|
||||
);
|
||||
proxySetter.setProxy(hProxy);
|
||||
stateSetter.setState(HState.CONNECTED);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (hProxy != null && b[0] == 0) {
|
||||
hProxy.getInHandler().act(packet);
|
||||
}
|
||||
else if (hProxy != null && b[0] == 1) {
|
||||
hProxy.getOutHandler().act(packet);
|
||||
}
|
||||
else {
|
||||
proxyProvider.abort();
|
||||
}
|
||||
}
|
||||
|
||||
@OnClose
|
||||
public void onClose(Session session) throws IOException {
|
||||
proxyProvider.abort();
|
||||
}
|
||||
|
||||
@OnError
|
||||
public void onError(Session session, Throwable throwable) {
|
||||
proxyProvider.abort();
|
||||
}
|
||||
}
|
@ -0,0 +1,27 @@
|
||||
package gearth.protocol.connection.proxy.unity;
|
||||
|
||||
import gearth.protocol.HConnection;
|
||||
import gearth.protocol.connection.HProxySetter;
|
||||
import gearth.protocol.connection.HStateSetter;
|
||||
import gearth.protocol.connection.proxy.ProxyProvider;
|
||||
|
||||
import javax.websocket.server.ServerEndpointConfig;
|
||||
|
||||
public class UnityCommunicatorConfig extends ServerEndpointConfig.Configurator {
|
||||
private final HProxySetter proxySetter;
|
||||
private final HStateSetter stateSetter;
|
||||
private final HConnection hConnection;
|
||||
private final ProxyProvider proxyProvider;
|
||||
|
||||
public UnityCommunicatorConfig(HProxySetter proxySetter, HStateSetter stateSetter, HConnection hConnection, ProxyProvider proxyProvider) {
|
||||
this.proxySetter = proxySetter;
|
||||
this.stateSetter = stateSetter;
|
||||
this.hConnection = hConnection;
|
||||
this.proxyProvider = proxyProvider;
|
||||
}
|
||||
|
||||
|
||||
public <T> T getEndpointInstance(Class<T> clazz) throws InstantiationException {
|
||||
return (T)new UnityCommunicator(proxySetter, stateSetter, hConnection, proxyProvider);
|
||||
}
|
||||
}
|
@ -0,0 +1,81 @@
|
||||
package gearth.protocol.connection.proxy.unity;
|
||||
|
||||
import gearth.protocol.HConnection;
|
||||
import gearth.protocol.connection.HProxySetter;
|
||||
import gearth.protocol.connection.HState;
|
||||
import gearth.protocol.connection.HStateSetter;
|
||||
import gearth.protocol.connection.proxy.ProxyProvider;
|
||||
import org.eclipse.jetty.server.Handler;
|
||||
import org.eclipse.jetty.server.Server;
|
||||
import org.eclipse.jetty.server.handler.HandlerList;
|
||||
import org.eclipse.jetty.servlet.ServletContextHandler;
|
||||
import org.eclipse.jetty.websocket.jsr356.server.deploy.WebSocketServerContainerInitializer;
|
||||
|
||||
import javax.websocket.server.ServerContainer;
|
||||
import javax.websocket.server.ServerEndpointConfig;
|
||||
import java.io.IOException;
|
||||
|
||||
public class UnityProxyProvider implements ProxyProvider {
|
||||
|
||||
private final HProxySetter proxySetter;
|
||||
private final HStateSetter stateSetter;
|
||||
private final HConnection hConnection;
|
||||
|
||||
private Server server;
|
||||
|
||||
public UnityProxyProvider(HProxySetter proxySetter, HStateSetter stateSetter, HConnection hConnection) {
|
||||
this.proxySetter = proxySetter;
|
||||
this.stateSetter = stateSetter;
|
||||
this.hConnection = hConnection;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public void start() throws IOException {
|
||||
|
||||
// https://happyhyppo.ro/2016/03/21/minimal-websockets-communication-with-javajetty-and-angularjs/
|
||||
server = new Server(8025);
|
||||
ServletContextHandler context = new ServletContextHandler(ServletContextHandler.SESSIONS);
|
||||
context.setContextPath("/ws");
|
||||
|
||||
HandlerList handlers = new HandlerList();
|
||||
handlers.setHandlers(new Handler[] { context });
|
||||
server.setHandler(handlers);
|
||||
|
||||
ServerContainer wscontainer = null;
|
||||
try {
|
||||
wscontainer = WebSocketServerContainerInitializer.configureContext(context);
|
||||
|
||||
wscontainer.addEndpoint(ServerEndpointConfig.Builder
|
||||
.create(UnityCommunicator.class, "/packethandler") // the endpoint url
|
||||
.configurator(new UnityCommunicatorConfig(proxySetter, stateSetter, hConnection, this))
|
||||
.build());
|
||||
|
||||
server.start();
|
||||
stateSetter.setState(HState.WAITING_FOR_CLIENT);
|
||||
} catch (Exception e) {
|
||||
stateSetter.setState(HState.NOT_CONNECTED);
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void abort() {
|
||||
if (server == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
final Server abortThis = server;
|
||||
stateSetter.setState(HState.ABORTING);
|
||||
new Thread(() -> {
|
||||
try {
|
||||
abortThis.stop();
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
} finally {
|
||||
stateSetter.setState(HState.NOT_CONNECTED);
|
||||
}
|
||||
}).start();
|
||||
server = null;
|
||||
}
|
||||
}
|
@ -7,7 +7,9 @@ import gearth.protocol.HPacket;
|
||||
import gearth.protocol.crypto.RC4;
|
||||
import gearth.protocol.memory.habboclient.HabboClient;
|
||||
import gearth.protocol.memory.habboclient.HabboClientFactory;
|
||||
import gearth.protocol.packethandler.*;
|
||||
import gearth.protocol.packethandler.flash.BufferChangeListener;
|
||||
import gearth.protocol.packethandler.flash.FlashPacketHandler;
|
||||
import gearth.protocol.packethandler.PayloadBuffer;
|
||||
import javafx.application.Platform;
|
||||
import javafx.scene.control.Alert;
|
||||
import javafx.scene.control.ButtonType;
|
||||
@ -25,17 +27,17 @@ public class Rc4Obtainer {
|
||||
public static final boolean DEBUG = false;
|
||||
|
||||
private HabboClient client;
|
||||
private List<PacketHandler> packetHandlers;
|
||||
private List<FlashPacketHandler> flashPacketHandlers;
|
||||
|
||||
public Rc4Obtainer(HConnection hConnection) {
|
||||
client = HabboClientFactory.get(hConnection);
|
||||
}
|
||||
|
||||
|
||||
public void setPacketHandlers(PacketHandler... packetHandlers) {
|
||||
this.packetHandlers = Arrays.asList(packetHandlers);
|
||||
public void setFlashPacketHandlers(FlashPacketHandler... flashPacketHandlers) {
|
||||
this.flashPacketHandlers = Arrays.asList(flashPacketHandlers);
|
||||
|
||||
for (PacketHandler handler : packetHandlers) {
|
||||
for (FlashPacketHandler handler : flashPacketHandlers) {
|
||||
BufferChangeListener bufferChangeListener = new BufferChangeListener() {
|
||||
@Override
|
||||
public void act() {
|
||||
@ -53,10 +55,10 @@ public class Rc4Obtainer {
|
||||
|
||||
|
||||
|
||||
private void onSendFirstEncryptedMessage(PacketHandler packetHandler) {
|
||||
private void onSendFirstEncryptedMessage(FlashPacketHandler flashPacketHandler) {
|
||||
if (!HConnection.DECRYPTPACKETS) return;
|
||||
|
||||
packetHandlers.forEach(PacketHandler::block);
|
||||
flashPacketHandlers.forEach(FlashPacketHandler::block);
|
||||
|
||||
new Thread(() -> {
|
||||
|
||||
@ -67,8 +69,8 @@ public class Rc4Obtainer {
|
||||
int i = 0;
|
||||
while (!worked && i < 4) {
|
||||
worked = (i % 2 == 0) ?
|
||||
onSendFirstEncryptedMessage(packetHandler, client.getRC4cached()) :
|
||||
onSendFirstEncryptedMessage(packetHandler, client.getRC4possibilities());
|
||||
onSendFirstEncryptedMessage(flashPacketHandler, client.getRC4cached()) :
|
||||
onSendFirstEncryptedMessage(flashPacketHandler, client.getRC4possibilities());
|
||||
i++;
|
||||
}
|
||||
|
||||
@ -107,16 +109,16 @@ public class Rc4Obtainer {
|
||||
System.out.println("Cracked RC4 in " + (endTime - startTime) + "ms");
|
||||
}
|
||||
|
||||
packetHandlers.forEach(PacketHandler::unblock);
|
||||
flashPacketHandlers.forEach(FlashPacketHandler::unblock);
|
||||
}).start();
|
||||
}
|
||||
|
||||
private boolean onSendFirstEncryptedMessage(PacketHandler packetHandler, List<byte[]> potentialRC4tables) {
|
||||
private boolean onSendFirstEncryptedMessage(FlashPacketHandler flashPacketHandler, List<byte[]> potentialRC4tables) {
|
||||
for (byte[] possible : potentialRC4tables) {
|
||||
|
||||
byte[] encBuffer = new byte[packetHandler.getEncryptedBuffer().size()];
|
||||
byte[] encBuffer = new byte[flashPacketHandler.getEncryptedBuffer().size()];
|
||||
for (int i = 0; i < encBuffer.length; i++) {
|
||||
encBuffer[i] = packetHandler.getEncryptedBuffer().get(i);
|
||||
encBuffer[i] = flashPacketHandler.getEncryptedBuffer().get(i);
|
||||
}
|
||||
|
||||
for (int i = 0; i < 256; i++) {
|
||||
@ -124,7 +126,7 @@ public class Rc4Obtainer {
|
||||
byte[] keycpy = Arrays.copyOf(possible, possible.length);
|
||||
RC4 rc4Tryout = new RC4(keycpy, i, j);
|
||||
|
||||
if (packetHandler.getMessageSide() == HMessage.Direction.TOSERVER) rc4Tryout.undoRc4(encBuffer);
|
||||
if (flashPacketHandler.getMessageSide() == HMessage.Direction.TOSERVER) rc4Tryout.undoRc4(encBuffer);
|
||||
if (rc4Tryout.couldBeFresh()) {
|
||||
byte[] encDataCopy = Arrays.copyOf(encBuffer, encBuffer.length);
|
||||
RC4 rc4TryCopy = rc4Tryout.deepCopy();
|
||||
@ -135,7 +137,7 @@ public class Rc4Obtainer {
|
||||
HPacket[] checker = payloadBuffer.pushAndReceive(decoded);
|
||||
|
||||
if (payloadBuffer.peak().length == 0) {
|
||||
packetHandler.setRc4(rc4Tryout);
|
||||
flashPacketHandler.setRc4(rc4Tryout);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -0,0 +1,12 @@
|
||||
package gearth.protocol.packethandler;
|
||||
|
||||
public class ByteArrayUtils {
|
||||
|
||||
public static byte[] combineByteArrays(byte[] arr1, byte[] arr2) {
|
||||
byte[] combined = new byte[arr1.length + arr2.length];
|
||||
System.arraycopy(arr1,0,combined,0 ,arr1.length);
|
||||
System.arraycopy(arr2,0,combined,arr1.length,arr2.length);
|
||||
return combined;
|
||||
}
|
||||
|
||||
}
|
@ -1,125 +1,32 @@
|
||||
package gearth.protocol.packethandler;
|
||||
|
||||
import gearth.misc.listenerpattern.Observable;
|
||||
import gearth.protocol.HConnection;
|
||||
import gearth.protocol.HMessage;
|
||||
import gearth.protocol.HPacket;
|
||||
import gearth.protocol.TrafficListener;
|
||||
import gearth.protocol.crypto.RC4;
|
||||
import gearth.services.extensionhandler.ExtensionHandler;
|
||||
import gearth.services.extensionhandler.OnHMessageHandled;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.OutputStream;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
public abstract class PacketHandler {
|
||||
|
||||
protected static final boolean DEBUG = false;
|
||||
protected final ExtensionHandler extensionHandler;
|
||||
private final Object[] trafficObservables; //get notified on packet send
|
||||
protected final PayloadBuffer payloadBuffer;
|
||||
protected volatile int currentIndex = 0;
|
||||
protected final Object sendLock = new Object();
|
||||
|
||||
private volatile PayloadBuffer payloadBuffer = new PayloadBuffer();
|
||||
private volatile OutputStream out;
|
||||
private volatile ExtensionHandler extensionHandler;
|
||||
private volatile Object[] trafficObservables; //get notified on packet send
|
||||
private volatile boolean isTempBlocked = false;
|
||||
volatile boolean isDataStream = false;
|
||||
private volatile int currentIndex = 0;
|
||||
|
||||
private final Object manipulationLock = new Object();
|
||||
private final Object sendLock = new Object();
|
||||
|
||||
private RC4 decryptcipher = null;
|
||||
private RC4 encryptcipher = null;
|
||||
|
||||
private volatile List<Byte> tempEncryptedBuffer = new ArrayList<>();
|
||||
volatile boolean isEncryptedStream = false;
|
||||
|
||||
|
||||
PacketHandler(OutputStream outputStream, Object[] trafficObservables, ExtensionHandler extensionHandler) {
|
||||
this.trafficObservables = trafficObservables;
|
||||
protected PacketHandler(ExtensionHandler extensionHandler, Object[] trafficObservables) {
|
||||
this.extensionHandler = extensionHandler;
|
||||
out = outputStream;
|
||||
}
|
||||
|
||||
public boolean isDataStream() {return isDataStream;}
|
||||
public void setAsDataStream() {
|
||||
isDataStream = true;
|
||||
}
|
||||
|
||||
public boolean isEncryptedStream() {
|
||||
return isEncryptedStream;
|
||||
}
|
||||
|
||||
public void act(byte[] buffer) throws IOException {
|
||||
if (!isDataStream) {
|
||||
out.write(buffer);
|
||||
return;
|
||||
}
|
||||
|
||||
bufferChangeObservable.fireEvent();
|
||||
|
||||
if (!isEncryptedStream) {
|
||||
payloadBuffer.push(buffer);
|
||||
}
|
||||
else if (!HConnection.DECRYPTPACKETS) {
|
||||
synchronized (sendLock) {
|
||||
out.write(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);
|
||||
}
|
||||
|
||||
if (!isTempBlocked) {
|
||||
flush();
|
||||
}
|
||||
this.trafficObservables = trafficObservables;
|
||||
this.payloadBuffer = new PayloadBuffer();
|
||||
}
|
||||
|
||||
|
||||
public void setRc4(RC4 rc4) {
|
||||
this.decryptcipher = rc4.deepCopy();
|
||||
this.encryptcipher = rc4.deepCopy();
|
||||
public abstract void sendToStream(byte[] buffer);
|
||||
|
||||
byte[] encrbuffer = new byte[tempEncryptedBuffer.size()];
|
||||
for (int i = 0; i < tempEncryptedBuffer.size(); i++) {
|
||||
encrbuffer[i] = tempEncryptedBuffer.get(i);
|
||||
}
|
||||
public abstract void act(byte[] buffer) throws IOException;
|
||||
|
||||
try {
|
||||
act(encrbuffer);
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
tempEncryptedBuffer = null;
|
||||
}
|
||||
|
||||
public void block() {
|
||||
isTempBlocked = true;
|
||||
}
|
||||
public void unblock() {
|
||||
try {
|
||||
flush();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
isTempBlocked = false;
|
||||
}
|
||||
|
||||
/**
|
||||
* LISTENERS CAN EDIT THE MESSAGE BEFORE BEING SENT
|
||||
* @param message
|
||||
*/
|
||||
private void notifyListeners(int i, HMessage message) {
|
||||
protected void notifyListeners(int i, HMessage message) {
|
||||
((Observable<TrafficListener>) trafficObservables[i]).fireEvent(trafficListener -> {
|
||||
message.getPacket().resetReadIndex();
|
||||
trafficListener.onCapture(message);
|
||||
@ -127,72 +34,4 @@ public abstract class PacketHandler {
|
||||
message.getPacket().resetReadIndex();
|
||||
}
|
||||
|
||||
public void sendToStream(byte[] buffer) {
|
||||
synchronized (sendLock) {
|
||||
try {
|
||||
out.write(
|
||||
(!isEncryptedStream)
|
||||
? buffer
|
||||
: encryptcipher.rc4(buffer)
|
||||
);
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void flush() throws IOException {
|
||||
synchronized (manipulationLock) {
|
||||
HPacket[] hpackets = payloadBuffer.receive();
|
||||
|
||||
for (HPacket hpacket : hpackets){
|
||||
HMessage hMessage = new HMessage(hpacket, getMessageSide(), currentIndex);
|
||||
boolean isencrypted = isEncryptedStream;
|
||||
|
||||
OnHMessageHandled afterExtensionIntercept = hMessage1 -> {
|
||||
if (isDataStream) {
|
||||
notifyListeners(2, hMessage1);
|
||||
}
|
||||
|
||||
if (!hMessage1.isBlocked()) {
|
||||
synchronized (sendLock) {
|
||||
out.write(
|
||||
(!isencrypted)
|
||||
? hMessage1.getPacket().toBytes()
|
||||
: encryptcipher.rc4(hMessage1.getPacket().toBytes())
|
||||
);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
if (isDataStream) {
|
||||
notifyListeners(0, hMessage);
|
||||
notifyListeners(1, hMessage);
|
||||
extensionHandler.handle(hMessage, afterExtensionIntercept);
|
||||
}
|
||||
else {
|
||||
afterExtensionIntercept.finished(hMessage);
|
||||
}
|
||||
|
||||
currentIndex++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public abstract HMessage.Direction getMessageSide();
|
||||
|
||||
public List<Byte> getEncryptedBuffer() {
|
||||
return tempEncryptedBuffer;
|
||||
}
|
||||
|
||||
protected abstract void printForDebugging(byte[] bytes);
|
||||
|
||||
private Observable<BufferChangeListener> bufferChangeObservable = new Observable<>(BufferChangeListener::act);
|
||||
public Observable<BufferChangeListener> getBufferChangeObservable() {
|
||||
return bufferChangeObservable;
|
||||
}
|
||||
|
||||
public int getCurrentIndex() {
|
||||
return currentIndex;
|
||||
}
|
||||
}
|
||||
|
@ -14,7 +14,7 @@ public class PayloadBuffer {
|
||||
return receive();
|
||||
}
|
||||
public void push(byte[] tcpData) {
|
||||
buffer = buffer.length == 0 ? tcpData.clone() : combineByteArrays(buffer, tcpData);
|
||||
buffer = buffer.length == 0 ? tcpData.clone() : ByteArrayUtils.combineByteArrays(buffer, tcpData);
|
||||
}
|
||||
public HPacket[] receive() {
|
||||
if (buffer.length < 6) return new HPacket[0];
|
||||
@ -30,14 +30,6 @@ public class PayloadBuffer {
|
||||
}
|
||||
|
||||
|
||||
private byte[] combineByteArrays(byte[] arr1, byte[] arr2) {
|
||||
byte[] combined = new byte[arr1.length + arr2.length];
|
||||
System.arraycopy(arr1,0,combined,0 ,arr1.length);
|
||||
System.arraycopy(arr2,0,combined,arr1.length,arr2.length);
|
||||
return combined;
|
||||
}
|
||||
|
||||
|
||||
public byte[] peak() {
|
||||
return buffer;
|
||||
}
|
||||
|
@ -1,4 +1,4 @@
|
||||
package gearth.protocol.packethandler;
|
||||
package gearth.protocol.packethandler.flash;
|
||||
|
||||
|
||||
public interface BufferChangeListener {
|
@ -0,0 +1,182 @@
|
||||
package gearth.protocol.packethandler.flash;
|
||||
|
||||
import gearth.misc.listenerpattern.Observable;
|
||||
import gearth.protocol.HConnection;
|
||||
import gearth.protocol.HMessage;
|
||||
import gearth.protocol.HPacket;
|
||||
import gearth.protocol.TrafficListener;
|
||||
import gearth.protocol.crypto.RC4;
|
||||
import gearth.protocol.packethandler.PacketHandler;
|
||||
import gearth.protocol.packethandler.PayloadBuffer;
|
||||
import gearth.services.extensionhandler.ExtensionHandler;
|
||||
import gearth.services.extensionhandler.OnHMessageHandled;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.OutputStream;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
public abstract class FlashPacketHandler extends PacketHandler {
|
||||
|
||||
protected static final boolean DEBUG = false;
|
||||
|
||||
private volatile OutputStream out;
|
||||
private volatile boolean isTempBlocked = false;
|
||||
volatile boolean isDataStream = false;
|
||||
|
||||
private final Object manipulationLock = new Object();
|
||||
|
||||
private RC4 decryptcipher = null;
|
||||
private RC4 encryptcipher = null;
|
||||
|
||||
private volatile List<Byte> tempEncryptedBuffer = new ArrayList<>();
|
||||
volatile boolean isEncryptedStream = false;
|
||||
|
||||
|
||||
FlashPacketHandler(OutputStream outputStream, Object[] trafficObservables, ExtensionHandler extensionHandler) {
|
||||
super(extensionHandler, trafficObservables);
|
||||
out = outputStream;
|
||||
}
|
||||
|
||||
public boolean isDataStream() {return isDataStream;}
|
||||
public void setAsDataStream() {
|
||||
isDataStream = true;
|
||||
}
|
||||
|
||||
public boolean isEncryptedStream() {
|
||||
return isEncryptedStream;
|
||||
}
|
||||
|
||||
public void act(byte[] buffer) throws IOException {
|
||||
if (!isDataStream) {
|
||||
out.write(buffer);
|
||||
return;
|
||||
}
|
||||
|
||||
bufferChangeObservable.fireEvent();
|
||||
|
||||
if (!isEncryptedStream) {
|
||||
payloadBuffer.push(buffer);
|
||||
}
|
||||
else if (!HConnection.DECRYPTPACKETS) {
|
||||
synchronized (sendLock) {
|
||||
out.write(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);
|
||||
}
|
||||
|
||||
if (!isTempBlocked) {
|
||||
flush();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public void setRc4(RC4 rc4) {
|
||||
this.decryptcipher = 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() {
|
||||
isTempBlocked = true;
|
||||
}
|
||||
public void unblock() {
|
||||
try {
|
||||
flush();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
isTempBlocked = false;
|
||||
}
|
||||
|
||||
public void sendToStream(byte[] buffer) {
|
||||
synchronized (sendLock) {
|
||||
try {
|
||||
out.write(
|
||||
(!isEncryptedStream)
|
||||
? buffer
|
||||
: encryptcipher.rc4(buffer)
|
||||
);
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void flush() throws IOException {
|
||||
synchronized (manipulationLock) {
|
||||
HPacket[] hpackets = payloadBuffer.receive();
|
||||
|
||||
for (HPacket hpacket : hpackets){
|
||||
HMessage hMessage = new HMessage(hpacket, getMessageSide(), currentIndex);
|
||||
boolean isencrypted = isEncryptedStream;
|
||||
|
||||
OnHMessageHandled afterExtensionIntercept = hMessage1 -> {
|
||||
if (isDataStream) {
|
||||
notifyListeners(2, hMessage1);
|
||||
}
|
||||
|
||||
if (!hMessage1.isBlocked()) {
|
||||
synchronized (sendLock) {
|
||||
out.write(
|
||||
(!isencrypted)
|
||||
? hMessage1.getPacket().toBytes()
|
||||
: encryptcipher.rc4(hMessage1.getPacket().toBytes())
|
||||
);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
if (isDataStream) {
|
||||
notifyListeners(0, hMessage);
|
||||
notifyListeners(1, hMessage);
|
||||
extensionHandler.handle(hMessage, afterExtensionIntercept);
|
||||
}
|
||||
else {
|
||||
afterExtensionIntercept.finished(hMessage);
|
||||
}
|
||||
|
||||
currentIndex++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public abstract HMessage.Direction getMessageSide();
|
||||
|
||||
public List<Byte> getEncryptedBuffer() {
|
||||
return tempEncryptedBuffer;
|
||||
}
|
||||
|
||||
protected abstract void printForDebugging(byte[] bytes);
|
||||
|
||||
private Observable<BufferChangeListener> bufferChangeObservable = new Observable<>(BufferChangeListener::act);
|
||||
public Observable<BufferChangeListener> getBufferChangeObservable() {
|
||||
return bufferChangeObservable;
|
||||
}
|
||||
|
||||
public int getCurrentIndex() {
|
||||
return currentIndex;
|
||||
}
|
||||
}
|
@ -1,4 +1,4 @@
|
||||
package gearth.protocol.packethandler;
|
||||
package gearth.protocol.packethandler.flash;
|
||||
|
||||
import gearth.misc.listenerpattern.Observable;
|
||||
import gearth.protocol.HMessage;
|
||||
@ -6,13 +6,11 @@ import gearth.protocol.HPacket;
|
||||
import gearth.protocol.TrafficListener;
|
||||
import gearth.services.extensionhandler.ExtensionHandler;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.OutputStream;
|
||||
import java.util.List;
|
||||
|
||||
public class IncomingPacketHandler extends PacketHandler {
|
||||
public class IncomingFlashPacketHandler extends FlashPacketHandler {
|
||||
|
||||
public IncomingPacketHandler(OutputStream outputStream, Object[] trafficObservables, OutgoingPacketHandler outgoingHandler, ExtensionHandler extensionHandler) {
|
||||
public IncomingFlashPacketHandler(OutputStream outputStream, Object[] trafficObservables, OutgoingFlashPacketHandler outgoingHandler, ExtensionHandler extensionHandler) {
|
||||
super(outputStream, trafficObservables, extensionHandler);
|
||||
|
||||
TrafficListener listener = new TrafficListener() {
|
@ -1,4 +1,4 @@
|
||||
package gearth.protocol.packethandler;
|
||||
package gearth.protocol.packethandler.flash;
|
||||
|
||||
public interface OnDatastreamConfirmedListener {
|
||||
|
@ -1,4 +1,4 @@
|
||||
package gearth.protocol.packethandler;
|
||||
package gearth.protocol.packethandler.flash;
|
||||
|
||||
import gearth.misc.listenerpattern.Observable;
|
||||
import gearth.protocol.HMessage;
|
||||
@ -7,13 +7,10 @@ import gearth.services.extensionhandler.ExtensionHandler;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.OutputStream;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
public class OutgoingPacketHandler extends PacketHandler {
|
||||
public class OutgoingFlashPacketHandler extends FlashPacketHandler {
|
||||
|
||||
public OutgoingPacketHandler(OutputStream outputStream, Object[] trafficObservables, ExtensionHandler extensionHandler) {
|
||||
public OutgoingFlashPacketHandler(OutputStream outputStream, Object[] trafficObservables, ExtensionHandler extensionHandler) {
|
||||
super(outputStream, trafficObservables, extensionHandler);
|
||||
}
|
||||
|
@ -0,0 +1,59 @@
|
||||
package gearth.protocol.packethandler.unity;
|
||||
|
||||
import gearth.protocol.HMessage;
|
||||
import gearth.protocol.HPacket;
|
||||
import gearth.protocol.packethandler.ByteArrayUtils;
|
||||
import gearth.protocol.packethandler.PacketHandler;
|
||||
import gearth.protocol.packethandler.PayloadBuffer;
|
||||
import gearth.services.extensionhandler.ExtensionHandler;
|
||||
import gearth.services.extensionhandler.OnHMessageHandled;
|
||||
|
||||
import javax.websocket.Session;
|
||||
import java.io.IOException;
|
||||
import java.nio.ByteBuffer;
|
||||
|
||||
public class UnityPacketHandler extends PacketHandler {
|
||||
|
||||
private final Session session;
|
||||
private final HMessage.Direction direction;
|
||||
|
||||
public UnityPacketHandler(ExtensionHandler extensionHandler, Object[] trafficObservables, Session session, HMessage.Direction direction) {
|
||||
super(extensionHandler, trafficObservables);
|
||||
this.session = session;
|
||||
this.direction = direction;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void sendToStream(byte[] buffer) {
|
||||
synchronized (sendLock) {
|
||||
try {
|
||||
byte[] prefix = new byte[]{(direction == HMessage.Direction.TOCLIENT ? ((byte)0) : ((byte)1))};
|
||||
byte[] combined = ByteArrayUtils.combineByteArrays(prefix, buffer);
|
||||
|
||||
session.getBasicRemote().sendBinary(ByteBuffer.wrap(combined));
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void act(byte[] buffer) throws IOException {
|
||||
HPacket[] packets = payloadBuffer.pushAndReceive(buffer);
|
||||
|
||||
for (HPacket hPacket : packets) {
|
||||
HMessage hMessage = new HMessage(hPacket, direction, currentIndex);
|
||||
|
||||
OnHMessageHandled afterExtensionIntercept = hMessage1 -> {
|
||||
notifyListeners(2, hMessage1);
|
||||
sendToStream(hMessage1.getPacket().toBytes());
|
||||
};
|
||||
|
||||
notifyListeners(0, hMessage);
|
||||
notifyListeners(1, hMessage);
|
||||
extensionHandler.handle(hMessage, afterExtensionIntercept);
|
||||
|
||||
currentIndex++;
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,4 @@
|
||||
package gearth.services.g_chrome_tools;
|
||||
|
||||
public class UnityFileServer {
|
||||
}
|
@ -0,0 +1,4 @@
|
||||
package gearth.services.g_chrome_tools;
|
||||
|
||||
public class UnitywebModifyer {
|
||||
}
|
@ -168,12 +168,19 @@ public class ConnectionController extends SubForm {
|
||||
|
||||
btnConnect.setDisable(true);
|
||||
new Thread(() -> {
|
||||
if (useFlash()) {
|
||||
if (cbx_autodetect.isSelected()) {
|
||||
getHConnection().start();
|
||||
}
|
||||
else {
|
||||
getHConnection().start(inpHost.getEditor().getText(), Integer.parseInt(inpPort.getEditor().getText()));
|
||||
}
|
||||
}
|
||||
else {
|
||||
getHConnection().startUnity();
|
||||
}
|
||||
|
||||
|
||||
if (HConnection.DEBUG) System.out.println("connecting");
|
||||
}).start();
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user