Merge branch 'development' into feature/timer-days

This commit is contained in:
Sandro Coutinho
2018-01-02 17:46:50 +00:00
committed by GitHub
122 changed files with 6007 additions and 6158 deletions
+5 -3
View File
@@ -1,5 +1,7 @@
language: java language: java
dist: trusty
jdk: jdk:
- openjdk7 - openjdk7
- oraclejdk8 - oraclejdk8
@@ -32,7 +34,7 @@ env:
- secure: UG+b1tEgc8xv9x4r//2OAIK1RrYv6n209KTTFMMwcnAa7DI8HaP8nljRa5/VhDhuKHdlVrYH/tI90v7UVBs0GDVNwK5V17Io0fMm3FUGZekSthTCqqno5wAGa9r6a6mMLtSaSmIFeIKi0+0d2ZwplRuhj/dtEYjjBBj+kK8g4nE= - secure: UG+b1tEgc8xv9x4r//2OAIK1RrYv6n209KTTFMMwcnAa7DI8HaP8nljRa5/VhDhuKHdlVrYH/tI90v7UVBs0GDVNwK5V17Io0fMm3FUGZekSthTCqqno5wAGa9r6a6mMLtSaSmIFeIKi0+0d2ZwplRuhj/dtEYjjBBj+kK8g4nE=
- secure: St/fecUDInFBCRriYqgp2F8PU9/SooorgxD9Mrs+b0EsC7AbtSsQXvdIv2Lp6xzdQ0VSXPcLIhULPOYrmBKnGQ/NjXTIZXxnroyQxxnI6xyEWIZwiHRY/bKRJDRbQTxD9NL32szKiDSwnw7pu6llF4D64UqQvziq4Gm6VohU75M= - secure: St/fecUDInFBCRriYqgp2F8PU9/SooorgxD9Mrs+b0EsC7AbtSsQXvdIv2Lp6xzdQ0VSXPcLIhULPOYrmBKnGQ/NjXTIZXxnroyQxxnI6xyEWIZwiHRY/bKRJDRbQTxD9NL32szKiDSwnw7pu6llF4D64UqQvziq4Gm6VohU75M=
- secure: bD15GVZWowiknbfLavh8CxSh0GsnF5kT4kZ6ggCuUDGyj0mzqf7dNRnchQIKkCG0WRYyTrFN4pEiygeywWsipEeAVv9Xhx3cuUZmzeQaR5KCWabSwJ8gK6jZd1YhcWmM9vrdPHobZr65MP0y/8mu/Fovgky9dY7KDf4G3SebNrM= - secure: bD15GVZWowiknbfLavh8CxSh0GsnF5kT4kZ6ggCuUDGyj0mzqf7dNRnchQIKkCG0WRYyTrFN4pEiygeywWsipEeAVv9Xhx3cuUZmzeQaR5KCWabSwJ8gK6jZd1YhcWmM9vrdPHobZr65MP0y/8mu/Fovgky9dY7KDf4G3SebNrM=
- PARABOT_VERSION=2.6.6.6 - PARABOT_VERSION=2.6.8
cache: cache:
directories: directories:
@@ -56,7 +58,7 @@ deploy:
branch: branch:
- master - master
- development - development
jdk: 'oraclejdk7' jdk: 'openjdk7'
- provider: script - provider: script
script: "cp ./.travis/.travis.settings.xml $HOME/.m2/settings.xml && mvn package javadoc:javadoc deploy site:deploy" script: "cp ./.travis/.travis.settings.xml $HOME/.m2/settings.xml && mvn package javadoc:javadoc deploy site:deploy"
@@ -65,4 +67,4 @@ deploy:
repo: Parabot/Parabot repo: Parabot/Parabot
branch: branch:
- master - master
jdk: 'oraclejdk7' jdk: 'openjdk7'
+1 -1
View File
@@ -3,7 +3,7 @@
# Parabot # Parabot
Parabot V2.6.3. Parabot V2.6.8.
#### Links #### Links
+1 -1
View File
@@ -6,7 +6,7 @@
<groupId>org.parabot</groupId> <groupId>org.parabot</groupId>
<artifactId>client</artifactId> <artifactId>client</artifactId>
<version>2.6.6.6</version> <version>2.6.8</version>
<packaging>jar</packaging> <packaging>jar</packaging>
@@ -8,20 +8,20 @@ import org.parabot.environment.api.utils.Version;
* @author Everel * @author Everel
*/ */
public class Configuration extends org.parabot.api.Configuration { public class Configuration extends org.parabot.api.Configuration {
public static final String LOGIN_SERVER = "http://bdn.parabot.org/api/v2/users/login"; public static final String LOGIN_SERVER = "http://bdn.parabot.org/api/v2/users/login";
public static final String GET_SCRIPTS = "http://bdn.parabot.org/api/get.php?action=scripts_scripts&server="; public static final String GET_SCRIPTS = "http://bdn.parabot.org/api/get.php?action=scripts_scripts&server=";
public static final String GET_SCRIPT = "http://bdn.parabot.org/api/get.php?action=scripts_script&id="; public static final String GET_SCRIPT = "http://bdn.parabot.org/api/get.php?action=scripts_script&id=";
public static final String GET_SERVER_PROVIDERS = "http://bdn.parabot.org/api/get.php?action=server_providers"; public static final String GET_SERVER_PROVIDERS = "http://bdn.parabot.org/api/get.php?action=server_providers";
public static final String GET_SERVER_PROVIDER = "http://v3.bdn.parabot.org/api/bot/download/provider?nightly=%s&server=%s"; public static final String GET_SERVER_PROVIDER = "http://v3.bdn.parabot.org/api/bot/download/provider?nightly=%s&server=%s";
public static final String GET_SERVER_PROVIDER_INFO = "http://bdn.parabot.org/api/get.php?action=server_information&name="; public static final String GET_SERVER_PROVIDER_INFO = "http://bdn.parabot.org/api/get.php?action=server_information&name=";
public static final String GET_SERVER_SETTINGS = "http://bdn.parabot.org/api/get.php?action=get_settings"; public static final String GET_SERVER_SETTINGS = "http://bdn.parabot.org/api/get.php?action=get_settings";
public static final String GET_BOT_VERSION = "http://bdn.parabot.org/api/v2/bot/version"; public static final String GET_BOT_VERSION = "http://bdn.parabot.org/api/v2/bot/version";
public static final String API_DOWNLOAD_BOT = "http://v3.bdn.parabot.org/api/bot/download/client"; public static final String API_DOWNLOAD_BOT = "http://v3.bdn.parabot.org/api/bot/download/client";
public static final String DOWNLOAD_BOT = "http://bdn.parabot.org/versions/"; public static final String DOWNLOAD_BOT = "http://bdn.parabot.org/versions/";
public static final String REGISTRATION_PAGE = "https://www.parabot.org/community/register/"; public static final String REGISTRATION_PAGE = "https://www.parabot.org/community/register/";
public static final String GET_RANDOMS = "http://v3.bdn.parabot.org/api/bot/download/randoms"; public static final String GET_RANDOMS = "http://v3.bdn.parabot.org/api/bot/download/randoms";
public static final String DATA_API = "http://bdn.parabot.org/api/v2/data/"; public static final String DATA_API = "http://bdn.parabot.org/api/v2/data/";
public static final String ITEM_API = DATA_API + "items/"; public static final String ITEM_API = DATA_API + "items/";
public static final Version BOT_VERSION = ProjectProperties.getProjectVersion(); public static final Version BOT_VERSION = ProjectProperties.getProjectVersion();
} }
+78 -77
View File
@@ -33,25 +33,25 @@ import java.util.TimerTask;
*/ */
public class Context { public class Context {
public static final HashMap<ThreadGroup, Context> threadGroups = new HashMap<ThreadGroup, Context>(); public static final HashMap<ThreadGroup, Context> threadGroups = new HashMap<ThreadGroup, Context>();
private static ArrayList<Paintable> paintables = new ArrayList<Paintable>(); private static ArrayList<Paintable> paintables = new ArrayList<Paintable>();
private static Context instance; private static Context instance;
private static String username; private static String username;
private ASMClassLoader classLoader; private ASMClassLoader classLoader;
private ClassPath classPath; private ClassPath classPath;
private ServerProvider serverProvider; private ServerProvider serverProvider;
private Applet gameApplet; private Applet gameApplet;
private HookParser hookParser; private HookParser hookParser;
private Script runningScript; private Script runningScript;
private RandomHandler randomHandler; private RandomHandler randomHandler;
private Object clientInstance; private Object clientInstance;
private PaintDebugger paintDebugger; private PaintDebugger paintDebugger;
private Mouse mouse; private Mouse mouse;
private Keyboard keyboard; private Keyboard keyboard;
private PBKeyListener pbKeyListener; private PBKeyListener pbKeyListener;
private ServerProviderInfo providerInfo; private ServerProviderInfo providerInfo;
private JSONParser jsonParser; private JSONParser jsonParser;
private PrintStream defaultOut; private PrintStream defaultOut;
private PrintStream defaultErr = System.err; private PrintStream defaultErr = System.err;
@@ -77,7 +77,15 @@ public class Context {
} }
public static Context getInstance() { public static Context getInstance() {
return getInstance(null); return getInstance(null);
}
public static String getUsername() {
return username;
}
public static void setUsername(String username) {
Context.username = username;
} }
/** /**
@@ -88,12 +96,12 @@ public class Context {
} }
/** /**
* Sets the hook parser * Gets the mouse
* *
* @param hookParser * @return mouse
*/ */
public void setHookParser(final HookParser hookParser) { public Mouse getMouse() {
this.hookParser = hookParser; return mouse;
} }
/** /**
@@ -106,15 +114,14 @@ public class Context {
} }
/** /**
* Gets the mouse * Gets the keyboard
* *
* @return mouse * @return keyboard
*/ */
public Mouse getMouse() { public Keyboard getKeyboard() {
return mouse; return keyboard;
} }
/** /**
* Sets the keyboard * Sets the keyboard
* *
@@ -124,15 +131,6 @@ public class Context {
this.keyboard = keyboard; this.keyboard = keyboard;
} }
/**
* Gets the keyboard
*
* @return keyboard
*/
public Keyboard getKeyboard() {
return keyboard;
}
/** /**
* ClassPath * ClassPath
* *
@@ -160,44 +158,21 @@ public class Context {
return gameApplet; return gameApplet;
} }
/**
* Loads the game
*/
public void load() {
Core.verbose(TranslationHelper.translate("PARSING_SERVER_JAR"));
serverProvider.init();
serverProvider.parseJar();
Core.verbose(TranslationHelper.translate("DONE"));
Core.verbose(TranslationHelper.translate("INJECTING_HOOKS"));
serverProvider.injectHooks();
Core.verbose(TranslationHelper.translate("DONE"));
Core.verbose(TranslationHelper.translate("FETCHING_GAME_APPLET"));
if(Core.shouldDump()) {
Core.verbose(TranslationHelper.translate("DUMPING_INJECTED_CLIENT"));
classPath.dump(new File(Directories.getWorkspace(), "dump.jar"));
Core.verbose(TranslationHelper.translate("DONE"));
}
Applet applet = serverProvider.fetchApplet();
// if applet is null the server provider will call setApplet itself
if(applet != null) {
setApplet(applet);
}
}
/** /**
* Sets the bot target applet * Sets the bot target applet
*
* @param applet * @param applet
*/ */
public void setApplet(final Applet applet) { public void setApplet(final Applet applet) {
gameApplet = applet; gameApplet = applet;
if (getClient() == null) { if (getClient() == null) {
setClientInstance(gameApplet); setClientInstance(gameApplet);
} }
Core.verbose(TranslationHelper.translate("APPLET_FETCHED")); Core.verbose(TranslationHelper.translate("APPLET_FETCHED"));
final GamePanel panel = GamePanel.getInstance(); final GamePanel panel = GamePanel.getInstance();
final Dimension appletSize = serverProvider.getGameDimensions(); final Dimension appletSize = serverProvider.getGameDimensions();
panel.setPreferredSize(appletSize); panel.setPreferredSize(appletSize);
@@ -237,6 +212,30 @@ public class Context {
System.setErr(this.defaultErr); System.setErr(this.defaultErr);
} }
/**
* Loads the game
*/
public void load() {
Core.verbose(TranslationHelper.translate("PARSING_SERVER_JAR"));
serverProvider.init();
serverProvider.parseJar();
Core.verbose(TranslationHelper.translate("DONE"));
Core.verbose(TranslationHelper.translate("INJECTING_HOOKS"));
serverProvider.injectHooks();
Core.verbose(TranslationHelper.translate("DONE"));
Core.verbose(TranslationHelper.translate("FETCHING_GAME_APPLET"));
if (Core.shouldDump()) {
Core.verbose(TranslationHelper.translate("DUMPING_INJECTED_CLIENT"));
classPath.dump(new File(Directories.getWorkspace(), "dump.jar"));
Core.verbose(TranslationHelper.translate("DONE"));
}
Applet applet = serverProvider.fetchApplet();
// if applet is null the server provider will call setApplet itself
if (applet != null) {
setApplet(applet);
}
}
/** /**
* Gets the server prodiver belonging to this context * Gets the server prodiver belonging to this context
* *
@@ -247,22 +246,22 @@ public class Context {
} }
/** /**
*
* Sets provider info of this context * Sets provider info of this context
* *
* @param providerInfo * @param providerInfo
*/ */
public void setProviderInfo(ServerProviderInfo providerInfo) { public void setProviderInfo(ServerProviderInfo providerInfo) {
this.providerInfo = providerInfo; this.providerInfo = providerInfo;
} }
/** /**
* Gets ServerProvider info * Gets ServerProvider info
* Can be null if this is not a public server provider * Can be null if this is not a public server provider
*
* @return info about this provider * @return info about this provider
*/ */
public ServerProviderInfo getServerProviderInfo() { public ServerProviderInfo getServerProviderInfo() {
return this.providerInfo; return this.providerInfo;
} }
/** /**
@@ -329,12 +328,12 @@ public class Context {
} }
/** /**
* Sets the current running script, if a script stops it will call this method with a null argument * Sets the hook parser
* *
* @param script * @param hookParser
*/ */
public void setRunningScript(final Script script) { public void setHookParser(final HookParser hookParser) {
this.runningScript = script; this.hookParser = hookParser;
} }
/** /**
@@ -346,20 +345,22 @@ public class Context {
return this.runningScript; return this.runningScript;
} }
/**
* Sets the current running script, if a script stops it will call this method with a null argument
*
* @param script
*/
public void setRunningScript(final Script script) {
this.runningScript = script;
}
/** /**
* Gets the random handler * Gets the random handler
*
* @return random handler * @return random handler
*/ */
public RandomHandler getRandomHandler() { public RandomHandler getRandomHandler() {
return this.randomHandler; return this.randomHandler;
}
public static String getUsername() {
return username;
}
public static void setUsername(String username) {
Context.username = username;
} }
public JSONParser getJsonParser() { public JSONParser getJsonParser() {
@@ -18,6 +18,14 @@ public class ProjectProperties {
setProperties(); setProperties();
} }
public static Version getProjectVersion() {
return new Version(getInstance().getCached().getProperty("application.version"));
}
public static ProjectProperties getInstance() {
return instance == null ? instance = new ProjectProperties() : instance;
}
private void setProperties() { private void setProperties() {
InputStream input; InputStream input;
try { try {
@@ -35,12 +43,4 @@ public class ProjectProperties {
private Properties getCached() { private Properties getCached() {
return cached; return cached;
} }
public static Version getProjectVersion() {
return new Version(getInstance().getCached().getProperty("application.version"));
}
public static ProjectProperties getInstance() {
return instance == null ? instance = new ProjectProperties() : instance;
}
} }
@@ -1,6 +1,5 @@
package org.parabot.core.asm; package org.parabot.core.asm;
import org.objectweb.asm.ClassWriter; import org.objectweb.asm.ClassWriter;
import org.objectweb.asm.tree.ClassNode; import org.objectweb.asm.tree.ClassNode;
import org.parabot.core.classpath.ClassPath; import org.parabot.core.classpath.ClassPath;
@@ -16,92 +15,90 @@ import java.util.HashMap;
import java.util.Map; import java.util.Map;
/** /**
*
* Makes classnodes into runnable classes * Makes classnodes into runnable classes
* *
* @author Everel * @author Everel
* @author Matt * @author Matt
*
*/ */
public class ASMClassLoader extends ClassLoader { public class ASMClassLoader extends ClassLoader {
private Map<String, Class<?>> classCache; public ClassPath classPath;
public ClassPath classPath; private Map<String, Class<?>> classCache;
public ASMClassLoader(final ClassPath classPath) { public ASMClassLoader(final ClassPath classPath) {
this.classCache = new HashMap<String, Class<?>>(); this.classCache = new HashMap<String, Class<?>>();
this.classPath = classPath; this.classPath = classPath;
} }
@Override @Override
protected URL findResource(String name) { protected URL findResource(String name) {
if (getSystemResource(name) == null) { if (getSystemResource(name) == null) {
if (classPath.resources.containsKey(name)) { if (classPath.resources.containsKey(name)) {
try { try {
return classPath.resources.get(name).toURI().toURL(); return classPath.resources.get(name).toURI().toURL();
} catch (MalformedURLException e) { } catch (MalformedURLException e) {
e.printStackTrace(); e.printStackTrace();
return null; return null;
} }
} else { } else {
return null; return null;
} }
} }
return getSystemResource(name); return getSystemResource(name);
} }
@Override @Override
public Class<?> loadClass(String name) throws ClassNotFoundException { public Class<?> loadClass(String name) throws ClassNotFoundException {
return findClass(name); return findClass(name);
} }
@Override @Override
protected Class<?> findClass(String name) throws ClassNotFoundException { protected Class<?> findClass(String name) throws ClassNotFoundException {
try { try {
return getSystemClassLoader().loadClass(name); return getSystemClassLoader().loadClass(name);
} catch (Exception ignored) { } catch (Exception ignored) {
} }
String key = name.replace('.', '/'); String key = name.replace('.', '/');
if (classCache.containsKey(key)) { if (classCache.containsKey(key)) {
return classCache.get(key); return classCache.get(key);
} }
ClassNode node = classPath.classes.get(key); ClassNode node = classPath.classes.get(key);
if (node != null) { if (node != null) {
classPath.classes.remove(key); classPath.classes.remove(key);
Class<?> c = nodeToClass(node); Class<?> c = nodeToClass(node);
classCache.put(key, c); classCache.put(key, c);
return c; return c;
} }
return getSystemClassLoader().loadClass(name); return getSystemClassLoader().loadClass(name);
} }
private final Class<?> nodeToClass(ClassNode node) { private final Class<?> nodeToClass(ClassNode node) {
if (super.findLoadedClass(node.name) != null) { if (super.findLoadedClass(node.name) != null) {
return findLoadedClass(node.name); return findLoadedClass(node.name);
} }
ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS); ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS);
node.accept(cw); node.accept(cw);
byte[] b = cw.toByteArray(); byte[] b = cw.toByteArray();
return defineClass(node.name.replace('/', '.'), b, 0, b.length, return defineClass(node.name.replace('/', '.'), b, 0, b.length,
getDomain()); getDomain());
} }
private final ProtectionDomain getDomain() { private final ProtectionDomain getDomain() {
CodeSource code = null; CodeSource code = null;
try { try {
code = new CodeSource(new URL("http://www.url.com/"), (Certificate[]) null); code = new CodeSource(new URL("http://www.url.com/"), (Certificate[]) null);
} catch (MalformedURLException e) { } catch (MalformedURLException e) {
e.printStackTrace(); e.printStackTrace();
} }
return new ProtectionDomain(code, getPermissions()); return new ProtectionDomain(code, getPermissions());
} }
private final Permissions getPermissions() { private final Permissions getPermissions() {
Permissions permissions = new Permissions(); Permissions permissions = new Permissions();
permissions.add(new AllPermission()); permissions.add(new AllPermission());
return permissions; return permissions;
} }
} }
+130 -131
View File
@@ -9,151 +9,150 @@ import org.parabot.core.Context;
import java.lang.reflect.Modifier; import java.lang.reflect.Modifier;
/** /**
*
* A collection of various asm util methods * A collection of various asm util methods
* *
* @author Everel * @author Everel
*
*/ */
public class ASMUtils implements Opcodes { public class ASMUtils implements Opcodes {
public static FieldNode getField(ClassNode node, String fieldName) { public static FieldNode getField(ClassNode node, String fieldName) {
for (final Object fieldNode : node.fields) { for (final Object fieldNode : node.fields) {
FieldNode fieldNodeObject = (FieldNode) fieldNode; FieldNode fieldNodeObject = (FieldNode) fieldNode;
if (fieldNodeObject.name.equals(fieldName)) { if (fieldNodeObject.name.equals(fieldName)) {
return fieldNodeObject; return fieldNodeObject;
} }
} }
return null; return null;
} }
public static FieldNode getField(ClassNode node, String fieldName, String desc) { public static FieldNode getField(ClassNode node, String fieldName, String desc) {
if(desc == null) { if (desc == null) {
return getField(node, fieldName); return getField(node, fieldName);
} }
for (final Object fieldNode : node.fields) { for (final Object fieldNode : node.fields) {
FieldNode fieldNodeObject = (FieldNode) fieldNode; FieldNode fieldNodeObject = (FieldNode) fieldNode;
if (fieldNodeObject.name.equals(fieldName) && fieldNodeObject.desc.equals(desc)) { if (fieldNodeObject.name.equals(fieldName) && fieldNodeObject.desc.equals(desc)) {
return fieldNodeObject; return fieldNodeObject;
} }
} }
return null; return null;
} }
public static ClassNode getClass(String className) { public static ClassNode getClass(String className) {
Context context = Context.getInstance(); Context context = Context.getInstance();
for (ClassNode node : context.getClassPath().classes.values()) { for (ClassNode node : context.getClassPath().classes.values()) {
if (node.name.equals(className)) { if (node.name.equals(className)) {
return node; return node;
} }
} }
return null; return null;
} }
public static MethodNode getMethod(final String className, public static MethodNode getMethod(final String className,
final String methodName, final String methodDesc) { final String methodName, final String methodDesc) {
return getMethod(getClass(className), methodName, methodDesc); return getMethod(getClass(className), methodName, methodDesc);
} }
public static MethodNode getMethod(final ClassNode location, public static MethodNode getMethod(final ClassNode location,
final String methodName, final String methodDesc) { final String methodName, final String methodDesc) {
for (Object mn : location.methods) { for (Object mn : location.methods) {
MethodNode methodNode = (MethodNode) mn; MethodNode methodNode = (MethodNode) mn;
if (methodNode.name.equals(methodName) && methodNode.desc.equals(methodDesc)) { if (methodNode.name.equals(methodName) && methodNode.desc.equals(methodDesc)) {
return methodNode; return methodNode;
} }
} }
return null; return null;
} }
/** /**
* Return right opcode for desc * Return right opcode for desc
* *
* @param desc * @param desc
* @return return opcode *
*/ * @return return opcode
public static int getReturnOpcode(String desc) { */
desc = desc.substring(desc.indexOf("L") + 1); public static int getReturnOpcode(String desc) {
if (desc.length() > 1) { desc = desc.substring(desc.indexOf("L") + 1);
return ARETURN; if (desc.length() > 1) {
} return ARETURN;
final char c = desc.charAt(0); }
switch (c) { final char c = desc.charAt(0);
case 'I': switch (c) {
case 'Z': case 'I':
case 'B': case 'Z':
case 'S': case 'B':
case 'C': case 'S':
return IRETURN; case 'C':
case 'J': return IRETURN;
return LRETURN; case 'J':
case 'F': return LRETURN;
return FRETURN; case 'F':
case 'D': return FRETURN;
return DRETURN; case 'D':
case 'V': // void, method desc return DRETURN;
return RETURN; case 'V': // void, method desc
} return RETURN;
throw new RuntimeException("Wrong desc type: " + c); }
} throw new RuntimeException("Wrong desc type: " + c);
}
public static int getLoadOpcode(String desc) { public static int getLoadOpcode(String desc) {
desc = desc.substring(desc.indexOf("L") + 1); desc = desc.substring(desc.indexOf("L") + 1);
if (desc.length() > 1) { if (desc.length() > 1) {
return ALOAD; return ALOAD;
} }
final char c = desc.charAt(0); final char c = desc.charAt(0);
switch (c) { switch (c) {
case 'I': case 'I':
case 'Z': case 'Z':
case 'B': case 'B':
case 'S': case 'S':
case 'C': case 'C':
return ILOAD; return ILOAD;
case 'J': case 'J':
return LLOAD; return LLOAD;
case 'F': case 'F':
return FLOAD; return FLOAD;
case 'D': case 'D':
return DLOAD; return DLOAD;
} }
throw new RuntimeException("eek " + c); throw new RuntimeException("eek " + c);
} }
public static void makePublic(ClassNode node) { public static void makePublic(ClassNode node) {
if (!Modifier.isPublic(node.access)) { if (!Modifier.isPublic(node.access)) {
if (Modifier.isPrivate(node.access)) { if (Modifier.isPrivate(node.access)) {
node.access = node.access & (~Opcodes.ACC_PRIVATE); node.access = node.access & (~Opcodes.ACC_PRIVATE);
} }
if (Modifier.isProtected(node.access)) { if (Modifier.isProtected(node.access)) {
node.access = node.access & (~Opcodes.ACC_PROTECTED); node.access = node.access & (~Opcodes.ACC_PROTECTED);
} }
node.access = node.access | Opcodes.ACC_PUBLIC; node.access = node.access | Opcodes.ACC_PUBLIC;
} }
} }
public static void makePublic(MethodNode node) { public static void makePublic(MethodNode node) {
if (!Modifier.isPublic(node.access)) { if (!Modifier.isPublic(node.access)) {
if (Modifier.isPrivate(node.access)) { if (Modifier.isPrivate(node.access)) {
node.access = node.access & (~Opcodes.ACC_PRIVATE); node.access = node.access & (~Opcodes.ACC_PRIVATE);
} }
if (Modifier.isProtected(node.access)) { if (Modifier.isProtected(node.access)) {
node.access = node.access & (~Opcodes.ACC_PROTECTED); node.access = node.access & (~Opcodes.ACC_PROTECTED);
} }
node.access = node.access | Opcodes.ACC_PUBLIC; node.access = node.access | Opcodes.ACC_PUBLIC;
} }
} }
public static void makePublic(FieldNode node) { public static void makePublic(FieldNode node) {
if (!Modifier.isPublic(node.access)) { if (!Modifier.isPublic(node.access)) {
if (Modifier.isPrivate(node.access)) { if (Modifier.isPrivate(node.access)) {
node.access = node.access & (~Opcodes.ACC_PRIVATE); node.access = node.access & (~Opcodes.ACC_PRIVATE);
} }
if (Modifier.isProtected(node.access)) { if (Modifier.isProtected(node.access)) {
node.access = node.access & (~Opcodes.ACC_PROTECTED); node.access = node.access & (~Opcodes.ACC_PROTECTED);
} }
node.access = node.access | Opcodes.ACC_PUBLIC; node.access = node.access | Opcodes.ACC_PUBLIC;
} }
} }
} }
@@ -5,19 +5,20 @@ import org.objectweb.asm.commons.Remapper;
import java.util.HashMap; import java.util.HashMap;
public class ClassRemapper extends Remapper { public class ClassRemapper extends Remapper {
private static HashMap<String, String> remapNames = new HashMap<String, String>(); private static HashMap<String, String> remapNames = new HashMap<String, String>();
static {
remapNames.put("java/net/Socket", "org/parabot/core/network/proxy/ProxySocket");
remapNames.put("java/net/NetworkInterface", "org/parabot/core/network/NetworkInterface");
}
@Override static {
public String map(String str) { remapNames.put("java/net/Socket", "org/parabot/core/network/proxy/ProxySocket");
String s = remapNames.get(str); remapNames.put("java/net/NetworkInterface", "org/parabot/core/network/NetworkInterface");
if (s != null) { }
return s;
} else { @Override
return str; public String map(String str) {
} String s = remapNames.get(str);
} if (s != null) {
return s;
} else {
return str;
}
}
} }
@@ -16,124 +16,126 @@ import java.util.Map;
public class RedirectClassAdapter extends ClassVisitor implements Opcodes { public class RedirectClassAdapter extends ClassVisitor implements Opcodes {
private static final Map<String, Class<?>> redirects = new HashMap<String, Class<?>>(); private static final Map<String, Class<?>> redirects = new HashMap<String, Class<?>>();
private static PrintStream str_out, class_out;
private String className; static {
redirects.put("java/awt/Toolkit", ToolkitRedirect.class);
private static PrintStream str_out, class_out; redirects.put("java/lang/Class", ClassRedirect.class);
static {
redirects.put("java/awt/Toolkit", ToolkitRedirect.class);
redirects.put("java/lang/Class", ClassRedirect.class);
// redirects.put("java/lang/ClassLoader", ClassLoaderRedirect.class); // redirects.put("java/lang/ClassLoader", ClassLoaderRedirect.class);
redirects.put("java/lang/Runtime", RuntimeRedirect.class); redirects.put("java/lang/Runtime", RuntimeRedirect.class);
redirects.put("java/lang/Thread", ThreadRedirect.class); redirects.put("java/lang/Thread", ThreadRedirect.class);
redirects.put("java/lang/StackTraceElement", redirects.put("java/lang/StackTraceElement",
StackTraceElementRedirect.class); StackTraceElementRedirect.class);
redirects.put("java/lang/ProcessBuilder", ProcessBuilderRedirect.class); redirects.put("java/lang/ProcessBuilder", ProcessBuilderRedirect.class);
redirects.put("java/lang/System", SystemRedirect.class); redirects.put("java/lang/System", SystemRedirect.class);
} }
public RedirectClassAdapter(ClassVisitor cv) { private String className;
super(ASM5, cv);
if (str_out == null && Core.shouldDump())
try {
str_out = new PrintStream(new FileOutputStream(new File(Directories.getWorkspace(),"strings.txt")));
} catch (FileNotFoundException e) {
e.printStackTrace();
}
if(class_out == null && Core.shouldDump())
try {
class_out = new PrintStream(new FileOutputStream(new File(Directories.getWorkspace(),"classes.txt")));
} catch (FileNotFoundException e) {
e.printStackTrace();
}
}
@Override public RedirectClassAdapter(ClassVisitor cv) {
public void visit(int version, int access, String name, String signature, super(ASM5, cv);
String superName, String[] interfaces) { if (str_out == null && Core.shouldDump()) {
this.className = name; try {
super.visit(version, access, name, signature, superName, interfaces); str_out = new PrintStream(new FileOutputStream(new File(Directories.getWorkspace(), "strings.txt")));
if(class_out != null) { } catch (FileNotFoundException e) {
class_out.println(className + " References:"); e.printStackTrace();
} }
} }
if (class_out == null && Core.shouldDump()) {
try {
class_out = new PrintStream(new FileOutputStream(new File(Directories.getWorkspace(), "classes.txt")));
} catch (FileNotFoundException e) {
e.printStackTrace();
}
}
}
@Override public static SecurityException createSecurityException() {
public void visitEnd(){ Exception e = new Exception();
super.visitEnd(); StackTraceElement[] elements = e.getStackTrace();
if(class_out != null){ return new SecurityException("Unsafe operation blocked. Op:"
class_out.println(); + elements[1].getMethodName());
class_out.println(); }
}
}
@Override @Override
public MethodVisitor visitMethod(int access, String name, String desc, public void visit(int version, int access, String name, String signature,
String signature, String[] exceptions) { String superName, String[] interfaces) {
return new ReflectionMethodVisitor(name, desc, super.visitMethod( this.className = name;
access, name, desc, signature, exceptions)); super.visit(version, access, name, signature, superName, interfaces);
} if (class_out != null) {
class_out.println(className + " References:");
}
}
private class ReflectionMethodVisitor extends MethodVisitor { @Override
public void visitEnd() {
super.visitEnd();
if (class_out != null) {
class_out.println();
class_out.println();
}
}
public ReflectionMethodVisitor(String name, String desc, @Override
MethodVisitor mv) { public MethodVisitor visitMethod(int access, String name, String desc,
super(ASM5, mv); String signature, String[] exceptions) {
} return new ReflectionMethodVisitor(name, desc, super.visitMethod(
access, name, desc, signature, exceptions));
}
@Override private class ReflectionMethodVisitor extends MethodVisitor {
public void visitLdcInsn(Object o) {
if (o instanceof String && str_out != null) {
str_out.println(className + " " + o);
}
super.visitLdcInsn(o);
}
@Override public ReflectionMethodVisitor(String name, String desc,
public void visitMethodInsn(int opcode, String owner, String name, MethodVisitor mv) {
String desc, boolean itf) { super(ASM5, mv);
if (Core.isSecure()) { }
if (redirects.containsKey(owner) && !name.equals("<init>")
&& !name.equals("<clinit>")) {
if (opcode != INVOKESTATIC) {
desc = "(L" + owner + ";" + desc.substring(1);
}
opcode = INVOKESTATIC;
owner = redirects.get(owner).getName()
.replaceAll("\\.", "/");
}
}
if(class_out != null) { @Override
class_out.println(owner); public void visitLdcInsn(Object o) {
} if (o instanceof String && str_out != null) {
str_out.println(className + " " + o);
}
super.visitLdcInsn(o);
}
super.visitMethodInsn(opcode, owner, name, desc, itf); @Override
} public void visitMethodInsn(int opcode, String owner, String name,
String desc, boolean itf) {
if (Core.isSecure()) {
if (redirects.containsKey(owner) && !name.equals("<init>")
&& !name.equals("<clinit>")) {
if (opcode != INVOKESTATIC) {
desc = "(L" + owner + ";" + desc.substring(1);
}
opcode = INVOKESTATIC;
owner = redirects.get(owner).getName()
.replaceAll("\\.", "/");
}
}
@Override if (class_out != null) {
public void visitFieldInsn(int opcode, String owner, String name, class_out.println(owner);
String desc){ }
if (Core.isSecure() && (opcode == GETSTATIC || opcode == PUTSTATIC)) {
if (redirects.containsKey(owner)) {
owner = redirects.get(owner).getName()
.replaceAll("\\.", "/");
}
}
if(class_out != null)
class_out.println(owner);
super.visitFieldInsn(opcode, owner, name, desc);
}
} super.visitMethodInsn(opcode, owner, name, desc, itf);
}
public static SecurityException createSecurityException() { @Override
Exception e = new Exception(); public void visitFieldInsn(int opcode, String owner, String name,
StackTraceElement[] elements = e.getStackTrace(); String desc) {
return new SecurityException("Unsafe operation blocked. Op:" if (Core.isSecure() && (opcode == GETSTATIC || opcode == PUTSTATIC)) {
+ elements[1].getMethodName()); if (redirects.containsKey(owner)) {
} owner = redirects.get(owner).getName()
.replaceAll("\\.", "/");
}
}
if (class_out != null) {
class_out.println(owner);
}
super.visitFieldInsn(opcode, owner, name, desc);
}
}
} }
@@ -1,98 +1,89 @@
package org.parabot.core.asm.adapters; package org.parabot.core.asm.adapters;
import java.lang.reflect.Modifier;
import org.objectweb.asm.Label; import org.objectweb.asm.Label;
import org.objectweb.asm.Opcodes; import org.objectweb.asm.Opcodes;
import org.objectweb.asm.Type; import org.objectweb.asm.Type;
import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.*;
import org.objectweb.asm.tree.InsnList;
import org.objectweb.asm.tree.InsnNode;
import org.objectweb.asm.tree.JumpInsnNode;
import org.objectweb.asm.tree.LabelNode;
import org.objectweb.asm.tree.MethodInsnNode;
import org.objectweb.asm.tree.MethodNode;
import org.objectweb.asm.tree.VarInsnNode;
import org.parabot.core.asm.ASMUtils; import org.parabot.core.asm.ASMUtils;
import org.parabot.core.asm.interfaces.Injectable; import org.parabot.core.asm.interfaces.Injectable;
import java.lang.reflect.Modifier;
/** /**
*
* Injects a callback, invokes a given static method * Injects a callback, invokes a given static method
* *
* @author Everel * @author Everel
*
*/ */
public class AddCallbackAdapter implements Injectable, Opcodes { public class AddCallbackAdapter implements Injectable, Opcodes {
private MethodNode method; private MethodNode method;
private String invokeClass; private String invokeClass;
private String invokeMethod; private String invokeMethod;
private String desc; private String desc;
private int[] args; private int[] args;
private boolean conditional; private boolean conditional;
public AddCallbackAdapter(final MethodNode method, public AddCallbackAdapter(final MethodNode method,
final String invokeClass, final String invokeMethod, final String invokeClass, final String invokeMethod,
final String desc, final int[] args, final boolean conditional) { final String desc, final int[] args, final boolean conditional) {
this.method = method; this.method = method;
this.invokeClass = invokeClass; this.invokeClass = invokeClass;
this.invokeMethod = invokeMethod; this.invokeMethod = invokeMethod;
this.desc = desc; this.desc = desc;
this.args = args; this.args = args;
this.conditional = conditional; this.conditional = conditional;
} }
@Override @Override
public void inject() { public void inject() {
final Type[] types = Type.getArgumentTypes(this.method.desc); final Type[] types = Type.getArgumentTypes(this.method.desc);
InsnList inject = new InsnList(); InsnList inject = new InsnList();
Label l0 = new Label(); Label l0 = new Label();
inject.add(new LabelNode(l0)); inject.add(new LabelNode(l0));
int offset = 0; int offset = 0;
for (int arg : args) { for (int arg : args) {
if(Modifier.isStatic(method.access)) { if (Modifier.isStatic(method.access)) {
int loadOpcode = ASMUtils.getLoadOpcode(types[arg] int loadOpcode = ASMUtils.getLoadOpcode(types[arg]
.getDescriptor()); .getDescriptor());
inject.add(new VarInsnNode(loadOpcode, arg + offset)); inject.add(new VarInsnNode(loadOpcode, arg + offset));
if(loadOpcode == Opcodes.LLOAD) { if (loadOpcode == Opcodes.LLOAD) {
offset++; offset++;
} }
} else {
inject.add(new VarInsnNode(ASMUtils.getLoadOpcode(types[arg]
.getDescriptor()), arg + 1));
}
}
inject.add(new MethodInsnNode(INVOKESTATIC,
this.invokeClass, this.invokeMethod,
this.desc));
if(this.conditional) {
LabelNode ln = new LabelNode(new Label());
inject.add(new JumpInsnNode(IFEQ, ln));
if(Type.getReturnType(method.desc).equals(Type.BOOLEAN_TYPE)) {
inject.add(new InsnNode(ICONST_1));
inject.add(new InsnNode(IRETURN));
} else { } else {
inject.add(new InsnNode(RETURN)); inject.add(new VarInsnNode(ASMUtils.getLoadOpcode(types[arg]
.getDescriptor()), arg + 1));
}
}
inject.add(new MethodInsnNode(INVOKESTATIC,
this.invokeClass, this.invokeMethod,
this.desc));
if (this.conditional) {
LabelNode ln = new LabelNode(new Label());
inject.add(new JumpInsnNode(IFEQ, ln));
if (Type.getReturnType(method.desc).equals(Type.BOOLEAN_TYPE)) {
inject.add(new InsnNode(ICONST_1));
inject.add(new InsnNode(IRETURN));
} else {
inject.add(new InsnNode(RETURN));
} }
inject.add(ln); inject.add(ln);
} }
if(method.name.startsWith("<") && !Modifier.isStatic(method.access)) { if (method.name.startsWith("<") && !Modifier.isStatic(method.access)) {
// find target // find target
AbstractInsnNode target = null; AbstractInsnNode target = null;
for(AbstractInsnNode node : this.method.instructions.toArray()) { for (AbstractInsnNode node : this.method.instructions.toArray()) {
if(node.getOpcode() == Opcodes.INVOKESPECIAL) { if (node.getOpcode() == Opcodes.INVOKESPECIAL) {
target = node; target = node;
break; break;
} }
} }
if(target != null) { if (target != null) {
this.method.instructions.insert(target, inject); this.method.instructions.insert(target, inject);
} }
} else { } else {
this.method.instructions.insert(inject); this.method.instructions.insert(inject);
} }
} }
} }
@@ -2,42 +2,37 @@ package org.parabot.core.asm.adapters;
import org.objectweb.asm.Label; import org.objectweb.asm.Label;
import org.objectweb.asm.Opcodes; import org.objectweb.asm.Opcodes;
import org.objectweb.asm.tree.ClassNode; import org.objectweb.asm.tree.*;
import org.objectweb.asm.tree.InsnList;
import org.objectweb.asm.tree.LabelNode;
import org.objectweb.asm.tree.LdcInsnNode;
import org.objectweb.asm.tree.MethodInsnNode;
import org.objectweb.asm.tree.MethodNode;
public class AddDebugAdapter { public class AddDebugAdapter {
private ClassNode owner; private ClassNode owner;
private MethodNode mn; private MethodNode mn;
public AddDebugAdapter(ClassNode owner, MethodNode mn) { public AddDebugAdapter(ClassNode owner, MethodNode mn) {
this.owner = owner; this.owner = owner;
this.mn = mn; this.mn = mn;
} }
public AddDebugAdapter(MethodNode mn) { public AddDebugAdapter(MethodNode mn) {
this.mn = mn; this.mn = mn;
} }
public void inject() { public void inject() {
InsnList inject = new InsnList(); InsnList inject = new InsnList();
Label l0 = new Label(); Label l0 = new Label();
inject.add(new LabelNode(l0)); inject.add(new LabelNode(l0));
String callString = owner.name + "." + mn.name + " " + mn.desc; String callString = owner.name + "." + mn.name + " " + mn.desc;
LdcInsnNode ldc = new LdcInsnNode(callString); LdcInsnNode ldc = new LdcInsnNode(callString);
MethodInsnNode methodNode = new MethodInsnNode(Opcodes.INVOKESTATIC, "org/parabot/core/Core", "debug", MethodInsnNode methodNode = new MethodInsnNode(Opcodes.INVOKESTATIC, "org/parabot/core/Core", "debug",
"(Ljava/lang/String;)V"); "(Ljava/lang/String;)V");
inject.add(ldc); inject.add(ldc);
inject.add(methodNode); inject.add(methodNode);
mn.instructions.insert(inject); mn.instructions.insert(inject);
} }
} }
@@ -1,7 +1,5 @@
package org.parabot.core.asm.adapters; package org.parabot.core.asm.adapters;
import java.lang.reflect.Modifier;
import org.objectweb.asm.Opcodes; import org.objectweb.asm.Opcodes;
import org.objectweb.asm.Type; import org.objectweb.asm.Type;
import org.objectweb.asm.tree.ClassNode; import org.objectweb.asm.tree.ClassNode;
@@ -11,174 +9,166 @@ import org.parabot.core.Core;
import org.parabot.core.asm.ASMUtils; import org.parabot.core.asm.ASMUtils;
import org.parabot.core.asm.interfaces.Injectable; import org.parabot.core.asm.interfaces.Injectable;
import java.lang.reflect.Modifier;
/** /**
* Adds a method into a Classnode which returns a field * Adds a method into a Classnode which returns a field
* *
* @author Everel * @author Everel
*
*/ */
public class AddGetterAdapter implements Opcodes, Injectable { public class AddGetterAdapter implements Opcodes, Injectable {
private ClassNode into; private ClassNode into;
private ClassNode fieldLocation; private ClassNode fieldLocation;
private FieldNode fieldNode; private FieldNode fieldNode;
private String methodName; private String methodName;
private String returnDesc; private String returnDesc;
private boolean staticField; private boolean staticField;
private boolean staticMethod; private boolean staticMethod;
private long multiplier; private long multiplier;
/** /**
* * @param into - classnode to inject getter method in
* @param into * @param fieldLocation - classnode where field is located
* - classnode to inject getter method in * @param fieldNode - field name to get
* @param fieldLocation * @param methodName - method name of getter
* - classnode where field is located * @param returnDesc - return type of method, can be null for default return
* @param fieldNode * @param staticMethod - pass true if you want the method to be static
* - field name to get * @param multiplier - if this field requires a multipli
* @param methodName */
* - method name of getter public AddGetterAdapter(final ClassNode into,
* @param returnDesc final ClassNode fieldLocation, final FieldNode fieldNode,
* - return type of method, can be null for default return final String methodName, final String returnDesc,
* @param staticMethod final boolean staticMethod, final long multiplier) {
* - pass true if you want the method to be static this.into = into;
* @param multiplier this.fieldLocation = fieldLocation;
* - if this field requires a multipli this.fieldNode = fieldNode;
*/ this.methodName = methodName;
public AddGetterAdapter(final ClassNode into, this.returnDesc = returnDesc == null ? fieldNode.desc : returnDesc;
final ClassNode fieldLocation, final FieldNode fieldNode, this.staticField = Modifier.isStatic(fieldNode.access);
final String methodName, final String returnDesc, this.staticMethod = staticMethod;
final boolean staticMethod, final long multiplier) { this.multiplier = multiplier;
this.into = into; }
this.fieldLocation = fieldLocation;
this.fieldNode = fieldNode;
this.methodName = methodName;
this.returnDesc = returnDesc == null ? fieldNode.desc : returnDesc;
this.staticField = Modifier.isStatic(fieldNode.access);
this.staticMethod = staticMethod;
this.multiplier = multiplier;
}
/** /**
* * @param fieldLocation
* @param fieldLocation * @param fieldNode
* @param fieldNode * @param methodName
* @param methodName */
*/ public AddGetterAdapter(final ClassNode fieldLocation,
public AddGetterAdapter(final ClassNode fieldLocation, final FieldNode fieldNode, final String methodName) {
final FieldNode fieldNode, final String methodName) { this.into = fieldLocation;
this.into = fieldLocation; this.fieldLocation = fieldLocation;
this.fieldLocation = fieldLocation; this.fieldNode = fieldNode;
this.fieldNode = fieldNode; this.methodName = methodName;
this.methodName = methodName; this.returnDesc = fieldNode.desc;
this.returnDesc = fieldNode.desc; this.staticField = Modifier.isStatic(fieldNode.access);
this.staticField = Modifier.isStatic(fieldNode.access); this.staticMethod = false;
this.staticMethod = false; }
}
/** /**
* Validates if this getter can be injected, if not a runtime exception is * Validates if this getter can be injected, if not a runtime exception is
* thrown * thrown
*/ */
public void validate() { public void validate() {
if (methodName == null) { if (methodName == null) {
throw new RuntimeException("Null method name"); throw new RuntimeException("Null method name");
} }
if (into == null) { if (into == null) {
final StringBuilder sb = new StringBuilder(); final StringBuilder sb = new StringBuilder();
sb.append("Into ClassNode is null, at : ").append(methodName) sb.append("Into ClassNode is null, at : ").append(methodName)
.append("()"); .append("()");
throw new RuntimeException(sb.toString()); throw new RuntimeException(sb.toString());
} }
if (fieldNode == null) { if (fieldNode == null) {
final StringBuilder sb = new StringBuilder(); final StringBuilder sb = new StringBuilder();
sb.append("FieldLocation ClassNode is null, at : ") sb.append("FieldLocation ClassNode is null, at : ")
.append(methodName).append("()"); .append(methodName).append("()");
throw new RuntimeException(sb.toString()); throw new RuntimeException(sb.toString());
} }
if (fieldNode == null) { if (fieldNode == null) {
final StringBuilder sb = new StringBuilder(); final StringBuilder sb = new StringBuilder();
sb.append("FieldNode is null, at : ").append(methodName) sb.append("FieldNode is null, at : ").append(methodName)
.append("()"); .append("()");
throw new RuntimeException(sb.toString()); throw new RuntimeException(sb.toString());
} }
for (final Object methodNode : into.methods) { for (final Object methodNode : into.methods) {
MethodNode methodNodeObject = (MethodNode) methodNode; MethodNode methodNodeObject = (MethodNode) methodNode;
if (methodNodeObject.name.equals(methodName)) { if (methodNodeObject.name.equals(methodName)) {
final Type[] args = Type.getArgumentTypes(methodNodeObject.desc); final Type[] args = Type.getArgumentTypes(methodNodeObject.desc);
if (args != null && args.length != 0) { if (args != null && args.length != 0) {
continue; continue;
} }
final StringBuilder sb = new StringBuilder(); final StringBuilder sb = new StringBuilder();
sb.append("Duplicated method detected. ").append(methodName) sb.append("Duplicated method detected. ").append(methodName)
.append("() in ").append(into.name); .append("() in ").append(into.name);
throw new RuntimeException(sb.toString()); throw new RuntimeException(sb.toString());
} }
} }
} }
/** /**
* Injects this the method getter * Injects this the method getter
*/ */
@Override @Override
public void inject() { public void inject() {
Core.verbose("Injecting: " + this.toString()); Core.verbose("Injecting: " + this.toString());
MethodNode method = new MethodNode(ACC_PUBLIC MethodNode method = new MethodNode(ACC_PUBLIC
| (staticMethod ? ACC_STATIC : 0), methodName, "()" | (staticMethod ? ACC_STATIC : 0), methodName, "()"
+ returnDesc, null, null); + returnDesc, null, null);
if (!staticField) { if (!staticField) {
method.visitVarInsn(ALOAD, 0); method.visitVarInsn(ALOAD, 0);
} }
if(staticField) { if (staticField) {
ASMUtils.makePublic(fieldNode); ASMUtils.makePublic(fieldNode);
} }
method.visitFieldInsn(staticField ? GETSTATIC : GETFIELD, method.visitFieldInsn(staticField ? GETSTATIC : GETFIELD,
fieldLocation.name, fieldNode.name, fieldNode.desc); fieldLocation.name, fieldNode.name, fieldNode.desc);
if (!fieldNode.desc.equals(returnDesc)) { if (!fieldNode.desc.equals(returnDesc)) {
if (returnDesc.contains("L")) { if (returnDesc.contains("L")) {
if (!returnDesc.contains("[")) { if (!returnDesc.contains("[")) {
method.visitTypeInsn(CHECKCAST, method.visitTypeInsn(CHECKCAST,
returnDesc.replaceFirst("L", "") returnDesc.replaceFirst("L", "")
.replaceAll(";", "")); .replaceAll(";", ""));
} else { } else {
method.visitTypeInsn(CHECKCAST, returnDesc); method.visitTypeInsn(CHECKCAST, returnDesc);
} }
} }
} }
if (multiplier != 0) { if (multiplier != 0) {
if (fieldNode.desc.equals("I") || fieldNode.desc.equals("S")) { if (fieldNode.desc.equals("I") || fieldNode.desc.equals("S")) {
method.visitInsn(I2L); method.visitInsn(I2L);
} }
method.visitLdcInsn(new Long(multiplier)); method.visitLdcInsn(new Long(multiplier));
method.visitInsn(LMUL); method.visitInsn(LMUL);
if (returnDesc.equals("I") || returnDesc.equals("S")) { if (returnDesc.equals("I") || returnDesc.equals("S")) {
method.visitInsn(L2I); method.visitInsn(L2I);
} }
if (returnDesc.equals("S")) { if (returnDesc.equals("S")) {
method.visitInsn(I2S); method.visitInsn(I2S);
} }
} else if (fieldNode.desc.equals("J") && returnDesc.equals("I")) { } else if (fieldNode.desc.equals("J") && returnDesc.equals("I")) {
method.visitInsn(L2I); method.visitInsn(L2I);
} else if (fieldNode.desc.equals("I") && returnDesc.equals("J")) { } else if (fieldNode.desc.equals("I") && returnDesc.equals("J")) {
method.visitInsn(I2L); method.visitInsn(I2L);
} }
method.visitInsn(ASMUtils.getReturnOpcode(returnDesc)); method.visitInsn(ASMUtils.getReturnOpcode(returnDesc));
method.visitMaxs(1, 1); method.visitMaxs(1, 1);
into.methods.add(method); into.methods.add(method);
} }
@Override @Override
public String toString() { public String toString() {
return new StringBuilder("[Injectable: getter, into classname: ") return new StringBuilder("[Injectable: getter, into classname: ")
.append(into.name).append(", field classname: ") .append(into.name).append(", field classname: ")
.append(fieldLocation.name).append(", field name: ") .append(fieldLocation.name).append(", field name: ")
.append(fieldNode.name).append(", field desc: ") .append(fieldNode.name).append(", field desc: ")
.append(fieldNode.desc).append(", method name: ") .append(fieldNode.desc).append(", method name: ")
.append(methodName).append(", return desc: ") .append(methodName).append(", return desc: ")
.append(returnDesc).append(", static method: ") .append(returnDesc).append(", static method: ")
.append(staticMethod).append(", static field: ") .append(staticMethod).append(", static field: ")
.append(staticField).append("]").toString(); .append(staticField).append("]").toString();
} }
} }
@@ -7,55 +7,53 @@ import org.parabot.core.asm.ASMUtils;
import org.parabot.core.asm.interfaces.Injectable; import org.parabot.core.asm.interfaces.Injectable;
/** /**
*
* This class appends an interface to a class * This class appends an interface to a class
* *
* @author Everel * @author Everel
*
*/ */
public class AddInterfaceAdapter implements Injectable { public class AddInterfaceAdapter implements Injectable {
private static String accessorPackage; private static String accessorPackage;
private ClassNode node; private ClassNode node;
private String interfaceClass; private String interfaceClass;
public AddInterfaceAdapter(ClassNode node, String interfaceClass) { public AddInterfaceAdapter(ClassNode node, String interfaceClass) {
this.node = node; this.node = node;
this.interfaceClass = interfaceClass; this.interfaceClass = interfaceClass;
} }
public AddInterfaceAdapter(String className, String interfaceClass) { public AddInterfaceAdapter(String className, String interfaceClass) {
this.node = ASMUtils.getClass(className); this.node = ASMUtils.getClass(className);
this.interfaceClass = interfaceClass; this.interfaceClass = interfaceClass;
} }
public static void setAccessorPackage(String packageName) { public static String getAccessorPackage() {
accessorPackage = packageName; return accessorPackage;
} }
public static String getAccessorPackage() { public static void setAccessorPackage(String packageName) {
return accessorPackage; accessorPackage = packageName;
} }
@Override protected static void addInterface(ClassNode node, String i) {
public void inject() { ASMUtils.makePublic(node);
Core.verbose("Injecting: " + this.toString()); for (Object mn : node.methods) {
addInterface(node, accessorPackage + interfaceClass); MethodNode methodNode = (MethodNode) mn;
} if (methodNode.name.startsWith("<init")) {
ASMUtils.makePublic(methodNode);
}
}
node.interfaces.add(i);
}
protected static void addInterface(ClassNode node, String i) { @Override
ASMUtils.makePublic(node); public void inject() {
for(Object mn : node.methods) { Core.verbose("Injecting: " + this.toString());
MethodNode methodNode = (MethodNode) mn; addInterface(node, accessorPackage + interfaceClass);
if(methodNode.name.startsWith("<init")) { }
ASMUtils.makePublic(methodNode);
}
}
node.interfaces.add(i);
}
@Override @Override
public String toString() { public String toString() {
return new StringBuilder("[Injectable: interface, into classname: ").append(node.name).append(", interface: ").append(accessorPackage).append(interfaceClass).append("]").toString(); return new StringBuilder("[Injectable: interface, into classname: ").append(node.name).append(", interface: ").append(accessorPackage).append(interfaceClass).append("]").toString();
} }
} }
@@ -1,7 +1,5 @@
package org.parabot.core.asm.adapters; package org.parabot.core.asm.adapters;
import java.lang.reflect.Modifier;
import org.objectweb.asm.Opcodes; import org.objectweb.asm.Opcodes;
import org.objectweb.asm.Type; import org.objectweb.asm.Type;
import org.objectweb.asm.tree.ClassNode; import org.objectweb.asm.tree.ClassNode;
@@ -9,109 +7,109 @@ import org.objectweb.asm.tree.MethodNode;
import org.parabot.core.asm.ASMUtils; import org.parabot.core.asm.ASMUtils;
import org.parabot.core.asm.interfaces.Injectable; import org.parabot.core.asm.interfaces.Injectable;
import java.lang.reflect.Modifier;
/** /**
*
* Injects a method which invokes an other method * Injects a method which invokes an other method
* *
* @author Everel * @author Everel
*
*/ */
public class AddInvokerAdapter implements Opcodes, Injectable { public class AddInvokerAdapter implements Opcodes, Injectable {
private ClassNode into; private ClassNode into;
private ClassNode methodLocation; private ClassNode methodLocation;
private MethodNode mn; private MethodNode mn;
private String argsDesc; private String argsDesc;
private String returnDesc; private String returnDesc;
private String methodName; private String methodName;
private boolean isInterface; private boolean isInterface;
private String instanceCast; private String instanceCast;
private String mName; private String mName;
private String mDesc; private String mDesc;
private String argsCheckCast; private String argsCheckCast;
private boolean isStatic; private boolean isStatic;
public AddInvokerAdapter(final ClassNode methodLocation, public AddInvokerAdapter(final ClassNode methodLocation,
final ClassNode into, final MethodNode mn, final String mName, final String mDesc, final String argsDesc, final ClassNode into, final MethodNode mn, final String mName, final String mDesc, final String argsDesc,
final String returnDesc, final String methodName, final String returnDesc, final String methodName,
boolean isInterface, String instanceCast, String argsCheckCastDesc) { boolean isInterface, String instanceCast, String argsCheckCastDesc) {
this.into = into; this.into = into;
this.methodLocation = methodLocation; this.methodLocation = methodLocation;
this.mName = mName; this.mName = mName;
this.mDesc = mDesc; this.mDesc = mDesc;
this.mn = mn; this.mn = mn;
this.argsDesc = argsDesc; this.argsDesc = argsDesc;
this.returnDesc = returnDesc; this.returnDesc = returnDesc;
this.methodName = methodName; this.methodName = methodName;
this.isInterface = isInterface; this.isInterface = isInterface;
this.instanceCast = instanceCast; this.instanceCast = instanceCast;
this.argsCheckCast = argsCheckCastDesc; this.argsCheckCast = argsCheckCastDesc;
} }
@Override @Override
public void inject() { public void inject() {
String mArgsDesc = argsCheckCast == null ? this.argsDesc : this.argsCheckCast; String mArgsDesc = argsCheckCast == null ? this.argsDesc : this.argsCheckCast;
MethodNode m = new MethodNode(ACC_PUBLIC, this.methodName, MethodNode m = new MethodNode(ACC_PUBLIC, this.methodName,
mArgsDesc + this.returnDesc, null, null); mArgsDesc + this.returnDesc, null, null);
if(!isInterface) { if (!isInterface) {
isStatic = (this.mn.access & ACC_STATIC) != 0; isStatic = (this.mn.access & ACC_STATIC) != 0;
if (!Modifier.isPublic(mn.access)) { if (!Modifier.isPublic(mn.access)) {
if (Modifier.isPrivate(mn.access)) { if (Modifier.isPrivate(mn.access)) {
mn.access = mn.access & (~ACC_PRIVATE); mn.access = mn.access & (~ACC_PRIVATE);
} }
if (Modifier.isProtected(mn.access)) { if (Modifier.isProtected(mn.access)) {
mn.access = mn.access & (~ACC_PROTECTED); mn.access = mn.access & (~ACC_PROTECTED);
} }
mn.access = mn.access | ACC_PUBLIC; mn.access = mn.access | ACC_PUBLIC;
//mn.access = mn.access | ACC_SYNCHRONIZED; //mn.access = mn.access | ACC_SYNCHRONIZED;
} }
} }
if(!isStatic || isInterface) { if (!isStatic || isInterface) {
m.visitVarInsn(ALOAD, 0); m.visitVarInsn(ALOAD, 0);
} }
if(instanceCast != null) { if (instanceCast != null) {
m.visitTypeInsn(CHECKCAST, instanceCast); m.visitTypeInsn(CHECKCAST, instanceCast);
} }
if (!this.argsDesc.equals("()")) { if (!this.argsDesc.equals("()")) {
Type[] castArgs = argsCheckCast == null ? null : Type.getArgumentTypes(argsCheckCast + "V"); Type[] castArgs = argsCheckCast == null ? null : Type.getArgumentTypes(argsCheckCast + "V");
Type[] methodArgs = Type.getArgumentTypes(argsDesc + "V"); Type[] methodArgs = Type.getArgumentTypes(argsDesc + "V");
for(int i = 0; i < methodArgs.length; i++) { for (int i = 0; i < methodArgs.length; i++) {
m.visitVarInsn(ASMUtils.getLoadOpcode(methodArgs[i].getDescriptor()), i + 1); m.visitVarInsn(ASMUtils.getLoadOpcode(methodArgs[i].getDescriptor()), i + 1);
if(castArgs != null && !castArgs[i].getDescriptor().equals(methodArgs[i].getDescriptor())) { if (castArgs != null && !castArgs[i].getDescriptor().equals(methodArgs[i].getDescriptor())) {
String cast = methodArgs[i].getDescriptor(); String cast = methodArgs[i].getDescriptor();
if(cast.startsWith("L")) { if (cast.startsWith("L")) {
cast = cast.substring(1).replace(";", ""); cast = cast.substring(1).replace(";", "");
} }
m.visitTypeInsn(CHECKCAST, cast); m.visitTypeInsn(CHECKCAST, cast);
} }
} }
} }
if(isInterface) { if (isInterface) {
m.visitMethodInsn(INVOKEINTERFACE, instanceCast, mName, mDesc); m.visitMethodInsn(INVOKEINTERFACE, instanceCast, mName, mDesc);
} else { } else {
m.visitMethodInsn(isStatic ? INVOKESTATIC : INVOKEVIRTUAL, methodLocation.name, mn.name, mn.desc); m.visitMethodInsn(isStatic ? INVOKESTATIC : INVOKEVIRTUAL, methodLocation.name, mn.name, mn.desc);
} }
if (this.returnDesc.contains("L")) { if (this.returnDesc.contains("L")) {
if (!this.returnDesc.contains("[")) { if (!this.returnDesc.contains("[")) {
m.visitTypeInsn(CHECKCAST, this.returnDesc m.visitTypeInsn(CHECKCAST, this.returnDesc
.replaceFirst("L", "").replaceAll(";", "")); .replaceFirst("L", "").replaceAll(";", ""));
} else { } else {
m.visitTypeInsn(CHECKCAST, this.returnDesc); m.visitTypeInsn(CHECKCAST, this.returnDesc);
} }
} }
m.visitInsn(ASMUtils.getReturnOpcode(this.returnDesc)); m.visitInsn(ASMUtils.getReturnOpcode(this.returnDesc));
m.visitMaxs(0, 0); m.visitMaxs(0, 0);
this.into.methods.add(m); this.into.methods.add(m);
} }
} }
@@ -11,75 +11,75 @@ import org.parabot.core.asm.interfaces.Injectable;
* Injects methods which sets a field * Injects methods which sets a field
* *
* @author Everel * @author Everel
*
*/ */
public class AddSetterAdapter implements Opcodes, Injectable { public class AddSetterAdapter implements Opcodes, Injectable {
private ClassNode fieldLocation; private ClassNode fieldLocation;
private ClassNode into; private ClassNode into;
private FieldNode field; private FieldNode field;
private String name; private String name;
private String desc; private String desc;
private boolean methodStatic; private boolean methodStatic;
public AddSetterAdapter(ClassNode fieldLocation, ClassNode into, public AddSetterAdapter(ClassNode fieldLocation, ClassNode into,
FieldNode field, String name, String desc, boolean methodStatic) { FieldNode field, String name, String desc, boolean methodStatic) {
this.fieldLocation = fieldLocation; this.fieldLocation = fieldLocation;
this.into = into; this.into = into;
this.field = field; this.field = field;
this.name = name; this.name = name;
this.desc = desc; this.desc = desc;
this.methodStatic = methodStatic; this.methodStatic = methodStatic;
} }
public AddSetterAdapter(ClassNode fieldLocation, ClassNode into, public AddSetterAdapter(ClassNode fieldLocation, ClassNode into,
FieldNode field, String name, String desc) { FieldNode field, String name, String desc) {
this(fieldLocation, into, field, name, desc, false); this(fieldLocation, into, field, name, desc, false);
} }
private static void addSetter(ClassNode fieldLocation, ClassNode into, private static void addSetter(ClassNode fieldLocation, ClassNode into,
FieldNode field, String name, String desc, boolean methodStatic) { FieldNode field, String name, String desc, boolean methodStatic) {
if (desc.contains("L") && !desc.endsWith("Ljava/lang/String;")) if (desc.contains("L") && !desc.endsWith("Ljava/lang/String;")) {
desc = "Ljava/lang/Object;"; desc = "Ljava/lang/Object;";
MethodNode method = new MethodNode(ACC_PUBLIC }
| (methodStatic ? ACC_STATIC : 0), name, "(" + desc + ")V", MethodNode method = new MethodNode(ACC_PUBLIC
null, null); | (methodStatic ? ACC_STATIC : 0), name, "(" + desc + ")V",
boolean isStatic = (field.access & ACC_STATIC) > 0; null, null);
if (!isStatic) { boolean isStatic = (field.access & ACC_STATIC) > 0;
method.visitVarInsn(ALOAD, 0); if (!isStatic) {
} method.visitVarInsn(ALOAD, 0);
if (desc.equals("I")) { }
method.visitVarInsn(ILOAD, 1); if (desc.equals("I")) {
} else if (desc.equals("J")) { method.visitVarInsn(ILOAD, 1);
method.visitVarInsn(Opcodes.LLOAD, 1); } else if (desc.equals("J")) {
} else { method.visitVarInsn(Opcodes.LLOAD, 1);
method.visitVarInsn(ALOAD, 1); } else {
} method.visitVarInsn(ALOAD, 1);
method.visitFieldInsn(isStatic ? PUTSTATIC : PUTFIELD, }
fieldLocation.name, field.name, field.desc); method.visitFieldInsn(isStatic ? PUTSTATIC : PUTFIELD,
method.visitInsn(RETURN); fieldLocation.name, field.name, field.desc);
method.visitMaxs(2, 2); method.visitInsn(RETURN);
into.methods.add(method); method.visitMaxs(2, 2);
} into.methods.add(method);
}
/** /**
* Injects the setter * Injects the setter
*/ */
@Override @Override
public void inject() { public void inject() {
Core.verbose("Injecting: " + this.toString()); Core.verbose("Injecting: " + this.toString());
addSetter(fieldLocation, into, field, name, desc, methodStatic); addSetter(fieldLocation, into, field, name, desc, methodStatic);
} }
@Override @Override
public String toString() { public String toString() {
return new StringBuilder("[Injectable: setter, into classname: ") return new StringBuilder("[Injectable: setter, into classname: ")
.append(into.name).append(", field classname: ") .append(into.name).append(", field classname: ")
.append(fieldLocation.name).append(", field name: ") .append(fieldLocation.name).append(", field name: ")
.append(field.name).append(", field desc: ").append(field.desc) .append(field.name).append(", field desc: ").append(field.desc)
.append(", method name: ").append(name) .append(", method name: ").append(name)
.append(", method desc: ").append(desc) .append(", method desc: ").append(desc)
.append(", static method: ").append(methodStatic).append("]") .append(", static method: ").append(methodStatic).append("]")
.toString(); .toString();
} }
} }
@@ -1,7 +1,5 @@
package org.parabot.core.asm.adapters; package org.parabot.core.asm.adapters;
import java.util.ListIterator;
import org.objectweb.asm.Opcodes; import org.objectweb.asm.Opcodes;
import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.AbstractInsnNode;
import org.objectweb.asm.tree.ClassNode; import org.objectweb.asm.tree.ClassNode;
@@ -11,60 +9,60 @@ import org.parabot.core.Core;
import org.parabot.core.asm.ASMUtils; import org.parabot.core.asm.ASMUtils;
import org.parabot.core.asm.interfaces.Injectable; import org.parabot.core.asm.interfaces.Injectable;
import java.util.ListIterator;
/** /**
*
* This class is used for changing the super class of a class * This class is used for changing the super class of a class
* *
* @author Everel * @author Everel
*
*/ */
public class AddSuperAdapter implements Injectable { public class AddSuperAdapter implements Injectable {
private ClassNode node; private ClassNode node;
private String superClass; private String superClass;
public AddSuperAdapter(final ClassNode node, final String superClass) { public AddSuperAdapter(final ClassNode node, final String superClass) {
this.node = node; this.node = node;
this.superClass = superClass; this.superClass = superClass;
} }
public AddSuperAdapter(final String className, final String superClass) { public AddSuperAdapter(final String className, final String superClass) {
this.node = ASMUtils.getClass(className); this.node = ASMUtils.getClass(className);
this.superClass = superClass; this.superClass = superClass;
} }
@Override private static final void setSuper(final ClassNode node,
public void inject() { final String superClass) {
Core.verbose("Injecting: " + this.toString()); ListIterator<?> mli = node.methods.listIterator();
setSuper(node, superClass); while (mli.hasNext()) {
} MethodNode mn = (MethodNode) mli.next();
if (mn.name.equals("<init>")) {
ListIterator<?> ili = mn.instructions.iterator();
while (ili.hasNext()) {
AbstractInsnNode ain = (AbstractInsnNode) ili.next();
if (ain.getOpcode() == Opcodes.INVOKESPECIAL) {
MethodInsnNode min = (MethodInsnNode) ain;
if (!min.owner.equals(node.name)) {
min.owner = superClass;
}
break;
}
}
}
}
node.superName = superClass;
}
private static final void setSuper(final ClassNode node, @Override
final String superClass) { public void inject() {
ListIterator<?> mli = node.methods.listIterator(); Core.verbose("Injecting: " + this.toString());
while (mli.hasNext()) { setSuper(node, superClass);
MethodNode mn = (MethodNode) mli.next(); }
if (mn.name.equals("<init>")) {
ListIterator<?> ili = mn.instructions.iterator();
while (ili.hasNext()) {
AbstractInsnNode ain = (AbstractInsnNode) ili.next();
if (ain.getOpcode() == Opcodes.INVOKESPECIAL) {
MethodInsnNode min = (MethodInsnNode) ain;
if(!min.owner.equals(node.name)) {
min.owner = superClass;
}
break;
}
}
}
}
node.superName = superClass;
}
@Override @Override
public String toString() { public String toString() {
return new StringBuilder("[Injectable: super, class name: ") return new StringBuilder("[Injectable: super, class name: ")
.append(node.name).append(", super: ").append(superClass) .append(node.name).append(", super: ").append(superClass)
.append("]").toString(); .append("]").toString();
} }
} }
@@ -1,50 +1,50 @@
package org.parabot.core.asm.hooks; package org.parabot.core.asm.hooks;
import java.io.File;
import java.io.InputStream;
import java.net.MalformedURLException;
import java.net.URL;
import org.parabot.core.parsers.hooks.HookParser; import org.parabot.core.parsers.hooks.HookParser;
import org.parabot.core.parsers.hooks.JSONHookParser; import org.parabot.core.parsers.hooks.JSONHookParser;
import org.parabot.core.parsers.hooks.XMLHookParser; import org.parabot.core.parsers.hooks.XMLHookParser;
import org.parabot.environment.api.utils.WebUtil; import org.parabot.environment.api.utils.WebUtil;
import java.io.File;
import java.io.InputStream;
import java.net.MalformedURLException;
import java.net.URL;
public class HookFile { public class HookFile {
public static final int TYPE_XML = 0; public static final int TYPE_XML = 0;
public static final int TYPE_JSON = 1; public static final int TYPE_JSON = 1;
private URL url; private URL url;
private int type; private int type;
public HookFile(File file, int type) throws MalformedURLException { public HookFile(File file, int type) throws MalformedURLException {
this(file.toURI().toURL(), type); this(file.toURI().toURL(), type);
} }
public HookFile(URL url, int type) { public HookFile(URL url, int type) {
setType(type); setType(type);
this.url = url; this.url = url;
} }
private void setType(int type) { private void setType(int type) {
if(type < 0 || type > 1) { if (type < 0 || type > 1) {
throw new IllegalArgumentException("This type does not exist"); throw new IllegalArgumentException("This type does not exist");
} }
this.type = type; this.type = type;
} }
public InputStream getInputStream() { public InputStream getInputStream() {
return WebUtil.getInputStream(url); return WebUtil.getInputStream(url);
} }
public HookParser getParser() { public HookParser getParser() {
switch(type) { switch (type) {
case TYPE_XML: case TYPE_XML:
return new XMLHookParser(this); return new XMLHookParser(this);
case TYPE_JSON: case TYPE_JSON:
return new JSONHookParser(this); return new JSONHookParser(this);
} }
return null; return null;
} }
} }
@@ -2,14 +2,14 @@ package org.parabot.core.asm.interfaces;
/** /**
* Injectable * Injectable
* @author Everel
* *
* @author Everel
*/ */
public interface Injectable { public interface Injectable {
/** /**
* Injects bytecode into a class * Injects bytecode into a class
*/ */
public void inject(); public void inject();
} }
@@ -12,13 +12,13 @@ public class ClassLoaderRedirect extends ClassLoader {
static int count = 0; static int count = 0;
public static Class<?>loadClass(ClassLoader c,String name){ public static Class<?> loadClass(ClassLoader c, String name) {
throw RedirectClassAdapter.createSecurityException(); throw RedirectClassAdapter.createSecurityException();
} }
public static ClassLoader getParent(ClassLoader c){ public static ClassLoader getParent(ClassLoader c) {
throw RedirectClassAdapter.createSecurityException(); throw RedirectClassAdapter.createSecurityException();
} }
public static URL getResource(ClassLoader classLoader, String name) { public static URL getResource(ClassLoader classLoader, String name) {
Core.verbose("#getResource requested for ClassLoaderRedirect (" + name + ")"); Core.verbose("#getResource requested for ClassLoaderRedirect (" + name + ")");
@@ -8,9 +8,22 @@ import java.io.InputStream;
import java.lang.annotation.Annotation; import java.lang.annotation.Annotation;
import java.lang.reflect.Field; import java.lang.reflect.Field;
import java.lang.reflect.Method; import java.lang.reflect.Method;
import java.security.AccessController;
import java.security.PrivilegedAction;
import java.security.ProtectionDomain;
public class ClassRedirect { public class ClassRedirect {
public static ProtectionDomain getProtectionDomain(final Class<?> clazz) {
System.err.println(clazz.getName() + " getProtectionDomain request granted.");
return AccessController.doPrivileged(new PrivilegedAction<ProtectionDomain>() {
public ProtectionDomain run() {
return clazz.getProtectionDomain();
}
});
}
public static Object newInstance(Class<?> c) throws IllegalAccessException, InstantiationException { public static Object newInstance(Class<?> c) throws IllegalAccessException, InstantiationException {
if (validStack()) { if (validStack()) {
return c.newInstance(); return c.newInstance();
@@ -136,8 +149,9 @@ public class ClassRedirect {
private static boolean validStack() { private static boolean validStack() {
Exception e = new Exception(); Exception e = new Exception();
for (StackTraceElement elem : e.getStackTrace()) { for (StackTraceElement elem : e.getStackTrace()) {
if (elem.getClassName().equals(Script.class.getName())) if (elem.getClassName().equals(Script.class.getName())) {
return true; return true;
}
} }
return false; return false;
} }
@@ -9,7 +9,7 @@ import java.util.ArrayList;
/** /**
* @author JKetelaar * @author JKetelaar
*/ */
public class FileRedirect extends File{ public class FileRedirect extends File {
private static ArrayList<String> cachedFiles = new ArrayList<>(); private static ArrayList<String> cachedFiles = new ArrayList<>();
@@ -35,57 +35,57 @@ public class FileRedirect extends File{
sout(uri.toString()); sout(uri.toString());
} }
public static boolean exists(File file){ public static boolean exists(File file) {
sout(file.toString()); sout(file.toString());
return file.exists(); return file.exists();
} }
public static boolean isFile(File file){ public static boolean isFile(File file) {
sout(file.toString()); sout(file.toString());
return file.isFile(); return file.isFile();
} }
public static long length(File file){ public static long length(File file) {
sout(file.toString()); sout(file.toString());
return file.length(); return file.length();
} }
public static boolean mkdirs(File file){ public static boolean mkdirs(File file) {
sout(file.toString()); sout(file.toString());
return file.mkdirs(); return file.mkdirs();
} }
public static boolean mkdir(File file){ public static boolean mkdir(File file) {
sout(file.toString()); sout(file.toString());
return file.mkdir(); return file.mkdir();
} }
public static boolean isDirectory(File file){ public static boolean isDirectory(File file) {
sout(file.toString()); sout(file.toString());
return file.isDirectory(); return file.isDirectory();
} }
public static String getAbsolutePath(File file){ public static String getAbsolutePath(File file) {
sout(file.toString()); sout(file.toString());
return file.getAbsolutePath(); return file.getAbsolutePath();
} }
public static File getAbsoluteFile(File file){ public static File getAbsoluteFile(File file) {
sout(file.toString()); sout(file.toString());
return file.getAbsoluteFile(); return file.getAbsoluteFile();
} }
public static File[] listFiles(File file){ public static File[] listFiles(File file) {
sout(file.toString()); sout(file.toString());
return file.listFiles(); return file.listFiles();
} }
public static String getName(File file){ public static String getName(File file) {
sout(file.getName()); sout(file.getName());
return file.getName(); return file.getName();
} }
private static void sout(String s){ private static void sout(String s) {
if (!cachedFiles.contains(s)) { if (!cachedFiles.contains(s)) {
Core.verbose("Server requested file: " + s); Core.verbose("Server requested file: " + s);
cachedFiles.add(s); cachedFiles.add(s);
@@ -2,8 +2,8 @@ package org.parabot.core.asm.redirect;
public class PacketCallback { public class PacketCallback {
public static void onPacket(String methodName,int value){ public static void onPacket(String methodName, int value) {
System.out.println(methodName + "(" + value + ")"); System.out.println(methodName + "(" + value + ")");
} }
} }
@@ -1,7 +1,6 @@
package org.parabot.core.asm.redirect; package org.parabot.core.asm.redirect;
import org.parabot.core.Core; import org.parabot.core.Core;
import org.parabot.core.Directories;
import java.io.InputStream; import java.io.InputStream;
import java.io.PrintStream; import java.io.PrintStream;
@@ -10,7 +9,7 @@ public class SystemRedirect {
public static PrintStream out = System.out; public static PrintStream out = System.out;
public static PrintStream err = System.err; public static PrintStream err = System.err;
public static InputStream in = System.in; public static InputStream in = System.in;
public static long currentTimeMillis() { public static long currentTimeMillis() {
return System.currentTimeMillis(); return System.currentTimeMillis();
@@ -1,66 +1,64 @@
package org.parabot.core.asm.redirect; package org.parabot.core.asm.redirect;
import org.parabot.core.Core;
import org.parabot.core.asm.RedirectClassAdapter; import org.parabot.core.asm.RedirectClassAdapter;
public class ThreadRedirect { public class ThreadRedirect {
private static int count = 0; private static int count = 0;
public static void start(Thread t){ public static void start(Thread t) {
t.start(); t.start();
} }
public static void setPriority(Thread t,int i){ public static void setPriority(Thread t, int i) {
t.setPriority(i); t.setPriority(i);
} }
public static void setDaemon(Thread t,boolean b){ public static void setDaemon(Thread t, boolean b) {
t.setDaemon(b); t.setDaemon(b);
} }
public static void interrupt(Thread t){ public static void interrupt(Thread t) {
t.interrupt(); t.interrupt();
} }
public static Thread currentThread(){ public static Thread currentThread() {
return null; return new Thread();
} }
public static void join(Thread t) throws InterruptedException{ public static void join(Thread t) throws InterruptedException {
t.join(); t.join();
} }
public static void join(Thread t,long l) throws InterruptedException{ public static void join(Thread t, long l) throws InterruptedException {
t.join(l); t.join(l);
} }
public static void join(Thread t, long l,int i) throws InterruptedException{ public static void join(Thread t, long l, int i) throws InterruptedException {
t.join(l, i); t.join(l, i);
} }
public static ClassLoader getContextClassLoader(Thread t){ public static ClassLoader getContextClassLoader(Thread t) {
return null; return null;
} }
public static ThreadGroup getThreadGroup(Thread t){ public static ThreadGroup getThreadGroup(Thread t) {
throw RedirectClassAdapter.createSecurityException(); throw RedirectClassAdapter.createSecurityException();
} }
public static void setName(Thread t, String name){ public static void setName(Thread t, String name) {
t.setName(name); t.setName(name);
} }
public static String getName(Thread t){ public static String getName(Thread t) {
return t.getName(); return t.getName();
} }
public static void sleep(long time) throws InterruptedException{ public static void sleep(long time) throws InterruptedException {
Thread.sleep(time); Thread.sleep(time);
} }
public static void setUncaughtExceptionHandler(Thread t, Thread.UncaughtExceptionHandler handler) {
public static void setUncaughtExceptionHandler(Thread t, Thread.UncaughtExceptionHandler handler){ t.setUncaughtExceptionHandler(handler);
t.setUncaughtExceptionHandler(handler); }
}
} }
@@ -5,69 +5,74 @@ import java.awt.datatransfer.Clipboard;
import java.awt.datatransfer.DataFlavor; import java.awt.datatransfer.DataFlavor;
import java.awt.datatransfer.Transferable; import java.awt.datatransfer.Transferable;
import java.awt.datatransfer.UnsupportedFlavorException; import java.awt.datatransfer.UnsupportedFlavorException;
import java.awt.image.ImageProducer;
import java.io.IOException; import java.io.IOException;
import java.net.URL; import java.net.URL;
public class ToolkitRedirect { public class ToolkitRedirect {
private static final Clipboard clipboard = new Clipboard("default"); private static final Clipboard clipboard = new Clipboard("default");
static{ static {
clipboard.setContents(new Transferable() { clipboard.setContents(new Transferable() {
@Override @Override
public DataFlavor[] getTransferDataFlavors() { public DataFlavor[] getTransferDataFlavors() {
return new DataFlavor[0]; return new DataFlavor[0];
} }
@Override @Override
public boolean isDataFlavorSupported(DataFlavor flavor) { public boolean isDataFlavorSupported(DataFlavor flavor) {
return false; return false;
} }
@Override @Override
public Object getTransferData(DataFlavor flavor) throws UnsupportedFlavorException, IOException { public Object getTransferData(DataFlavor flavor) throws UnsupportedFlavorException, IOException {
throw new UnsupportedFlavorException(flavor); throw new UnsupportedFlavorException(flavor);
} }
}, null); }, null);
} }
public static Toolkit getDefaultToolkit(){ public static Toolkit getDefaultToolkit() {
return Toolkit.getDefaultToolkit(); return Toolkit.getDefaultToolkit();
} }
public static Dimension getScreenSize(Toolkit t){ public static Dimension getScreenSize(Toolkit t) {
return new Dimension(0,0); return new Dimension(0, 0);
} }
public static Image createImage(Toolkit t,byte[] b){ public static Image createImage(Toolkit t, byte[] b) {
return null; return t.createImage(b);
} }
public static Image createImage(Toolkit t, String s){ public static Image createImage(Toolkit t, String s) {
return null; return t.createImage(s);
} }
public static Image getImage(Toolkit t,URL u){ public static Image createImage(Toolkit t, ImageProducer i) {
return t.getImage(u); return t.createImage(i);
} }
public static Image getImage(Toolkit t,String str){ public static Image getImage(Toolkit t, URL u) {
return t.getImage(str); return t.getImage(u);
} }
public static Cursor createCustomCursor(Toolkit t, Image i, Point p, String s){ public static Image getImage(Toolkit t, String str) {
return Cursor.getDefaultCursor(); return t.getImage(str);
} }
public static Clipboard getSystemClipboard(Toolkit toolkit){ public static Cursor createCustomCursor(Toolkit t, Image i, Point p, String s) {
return clipboard; return Cursor.getDefaultCursor();
} }
public static void sync(Toolkit toolkit){ public static Clipboard getSystemClipboard(Toolkit toolkit) {
toolkit.sync(); return clipboard;
} }
public static void sync(){ public static void sync(Toolkit toolkit) {
Toolkit.getDefaultToolkit().sync(); toolkit.sync();
} }
public static void sync() {
Toolkit.getDefaultToolkit().sync();
}
} }
@@ -3,6 +3,6 @@ package org.parabot.core.asm.redirect;
/** /**
* @author JKetelaar * @author JKetelaar
*/ */
public class URLRedirect{ public class URLRedirect {
} }
@@ -6,47 +6,45 @@ import org.parabot.core.asm.adapters.AddCallbackAdapter;
import org.parabot.core.asm.interfaces.Injectable; import org.parabot.core.asm.interfaces.Injectable;
/** /**
*
* This class is used for injecting a callback into a methodnode * This class is used for injecting a callback into a methodnode
* *
* @author Everel * @author Everel
*
*/ */
public class Callback implements Injectable { public class Callback implements Injectable {
private MethodNode method; private MethodNode method;
private String invokeClass; private String invokeClass;
private String invokeMethod; private String invokeMethod;
private String desc; private String desc;
private int[] args; private int[] args;
private boolean conditional; private boolean conditional;
public Callback(final String className, final String methodName, public Callback(final String className, final String methodName,
final String methodDesc, final String callbackClass, final String methodDesc, final String callbackClass,
final String callbackMethod, final String callbackDesc, String args, final boolean conditional) { final String callbackMethod, final String callbackDesc, String args, final boolean conditional) {
this.method = ASMUtils.getMethod(className, methodName, methodDesc); this.method = ASMUtils.getMethod(className, methodName, methodDesc);
this.invokeClass = callbackClass; this.invokeClass = callbackClass;
this.invokeMethod = callbackMethod; this.invokeMethod = callbackMethod;
this.desc = callbackDesc; this.desc = callbackDesc;
this.conditional = conditional; this.conditional = conditional;
if (args.contains(",")) { if (args.contains(",")) {
final String[] strArgs = args.split(","); final String[] strArgs = args.split(",");
this.args = new int[strArgs.length]; this.args = new int[strArgs.length];
for (int i = 0; i < this.args.length; i++) { for (int i = 0; i < this.args.length; i++) {
this.args[i] = Integer.parseInt(strArgs[i]); this.args[i] = Integer.parseInt(strArgs[i]);
} }
} else { } else {
this.args = new int[] { Integer.parseInt(args) }; this.args = new int[]{ Integer.parseInt(args) };
} }
} }
@Override @Override
public void inject() { public void inject() {
getAdapter().inject(); getAdapter().inject();
} }
public AddCallbackAdapter getAdapter() { public AddCallbackAdapter getAdapter() {
return new AddCallbackAdapter(this.method, this.invokeClass, return new AddCallbackAdapter(this.method, this.invokeClass,
this.invokeMethod, this.desc, this.args, this.conditional); this.invokeMethod, this.desc, this.args, this.conditional);
} }
} }
@@ -8,75 +8,73 @@ import org.parabot.core.asm.adapters.AddGetterAdapter;
import org.parabot.core.asm.interfaces.Injectable; import org.parabot.core.asm.interfaces.Injectable;
/** /**
*
* This class injects a getter which gets a specific field * This class injects a getter which gets a specific field
* *
* @author Everel * @author Everel
*
*/ */
public class Getter implements Injectable { public class Getter implements Injectable {
private ClassNode into; private ClassNode into;
private ClassNode fieldLocation; private ClassNode fieldLocation;
private FieldNode fieldNode; private FieldNode fieldNode;
private String methodName; private String methodName;
private String returnDesc; private String returnDesc;
private boolean staticMethod; private boolean staticMethod;
private long multiplier; private long multiplier;
/** /**
* * @param into - classnode to inject getter method in
* @param into - classnode to inject getter method in * @param fieldLocation - classnode where field is located
* @param fieldLocation - classnode where field is located * @param fieldNode - field name to get
* @param fieldNode - field name to get * @param methodName - method name of getter
* @param methodName - method name of getter * @param returnDesc - return type of method, can be null for default return
* @param returnDesc - return type of method, can be null for default return * @param staticMethod - pass true if you want the method to be static
* @param staticMethod - pass true if you want the method to be static * @param multiplier - if there is one, otherwise 0L
* @param multiplier - if there is one, otherwise 0L * @param fieldDesc - desc of the field, null if there are no duplicate field names
* @param fieldDesc - desc of the field, null if there are no duplicate field names */
*/ public Getter(final String into, final String fieldLocation, final String fieldNode,
public Getter(final String into, final String fieldLocation, final String fieldNode, final String methodName, final String returnDesc, final boolean staticMethod, final long multiplier,
final String methodName, final String returnDesc, final boolean staticMethod, final long multiplier, final String fieldDesc) {
final String fieldDesc) { this.into = ASMUtils.getClass(into);
this.into = ASMUtils.getClass(into); this.fieldLocation = ASMUtils.getClass(fieldLocation);
this.fieldLocation = ASMUtils.getClass(fieldLocation); this.fieldNode = ASMUtils.getField(ASMUtils.getClass(fieldLocation), fieldNode, fieldDesc);
this.fieldNode = ASMUtils.getField(ASMUtils.getClass(fieldLocation), fieldNode, fieldDesc); this.methodName = methodName;
this.methodName = methodName; this.returnDesc = returnDesc == null ? this.fieldNode.desc : returnDesc;
this.returnDesc = returnDesc == null ? this.fieldNode.desc : returnDesc; this.staticMethod = staticMethod;
this.staticMethod = staticMethod; this.multiplier = multiplier;
this.multiplier = multiplier; Core.verbose(methodName + "[" + fieldLocation + "." + fieldNode + "]");
Core.verbose(methodName + "[" + fieldLocation + "." + fieldNode + "]"); }
}
/** /**
* * @param fieldLocation
* @param fieldLocation * @param fieldNode
* @param fieldNode * @param methodName
* @param methodName */
*/ public Getter(final String fieldLocation, final String fieldNode, final String methodName) {
public Getter(final String fieldLocation, final String fieldNode, final String methodName) { this.into = ASMUtils.getClass(fieldLocation);
this.into = ASMUtils.getClass(fieldLocation); this.fieldLocation = this.into;
this.fieldLocation = this.into; this.fieldNode = ASMUtils.getField(this.into, fieldNode);
this.fieldNode = ASMUtils.getField(this.into, fieldNode); this.methodName = methodName;
this.methodName = methodName; this.returnDesc = this.fieldNode.desc;
this.returnDesc = this.fieldNode.desc; this.staticMethod = false;
this.staticMethod = false; }
}
/** /**
* Short route for getAdaptar().inject(); * Short route for getAdaptar().inject();
* @see AddGetterAdapter#inject *
*/ * @see AddGetterAdapter#inject
@Override */
public void inject() { @Override
public void inject() {
getAdapter().inject(); getAdapter().inject();
} }
/** /**
* Gets the AddGetterAdapter * Gets the AddGetterAdapter
* @return AddGetterAdapter *
*/ * @return AddGetterAdapter
public AddGetterAdapter getAdapter() { */
return new AddGetterAdapter(into, fieldLocation, fieldNode, methodName, returnDesc, staticMethod, multiplier); public AddGetterAdapter getAdapter() {
} return new AddGetterAdapter(into, fieldLocation, fieldNode, methodName, returnDesc, staticMethod, multiplier);
}
} }
@@ -4,41 +4,40 @@ import org.parabot.core.asm.adapters.AddInterfaceAdapter;
import org.parabot.core.asm.interfaces.Injectable; import org.parabot.core.asm.interfaces.Injectable;
/** /**
*
* This class appends an interface to a class * This class appends an interface to a class
* *
* @author Everel * @author Everel
*
*/ */
public class Interface implements Injectable { public class Interface implements Injectable {
private String className; private String className;
private String interfaceClass; private String interfaceClass;
public Interface(String className, String interfaceClass) { public Interface(String className, String interfaceClass) {
this.className = className; this.className = className;
this.interfaceClass = interfaceClass; this.interfaceClass = interfaceClass;
} }
/** /**
* Adds the interface to the class * Adds the interface to the class
* Short route for getAdapter#inject(); * Short route for getAdapter#inject();
*/ */
@Override @Override
public void inject() { public void inject() {
getAdapter().inject(); getAdapter().inject();
} }
/** /**
* Gets the add interface adapter * Gets the add interface adapter
* @return AddInterface adapter *
*/ * @return AddInterface adapter
public AddInterfaceAdapter getAdapter() { */
return new AddInterfaceAdapter(className, interfaceClass); public AddInterfaceAdapter getAdapter() {
} return new AddInterfaceAdapter(className, interfaceClass);
}
@Override @Override
public String toString() { public String toString() {
return String.format("%s implements %s%s", className, AddInterfaceAdapter.getAccessorPackage().replaceAll("/", "."), interfaceClass); return String.format("%s implements %s%s", className, AddInterfaceAdapter.getAccessorPackage().replaceAll("/", "."), interfaceClass);
} }
} }
@@ -1,5 +1,6 @@
package org.parabot.core.asm.wrappers; package org.parabot.core.asm.wrappers;
import org.objectweb.asm.Type;
import org.objectweb.asm.tree.ClassNode; import org.objectweb.asm.tree.ClassNode;
import org.objectweb.asm.tree.MethodNode; import org.objectweb.asm.tree.MethodNode;
import org.parabot.core.asm.ASMUtils; import org.parabot.core.asm.ASMUtils;
@@ -7,77 +8,75 @@ import org.parabot.core.asm.adapters.AddInvokerAdapter;
import org.parabot.core.asm.interfaces.Injectable; import org.parabot.core.asm.interfaces.Injectable;
/** /**
*
* This class is used for injecting an invoker into a methodnode * This class is used for injecting an invoker into a methodnode
* *
* @author Everel * @author Everel
*
*/ */
public class Invoker implements Injectable { public class Invoker implements Injectable {
private ClassNode into; private ClassNode into;
private ClassNode methodLocation; private ClassNode methodLocation;
private MethodNode mn; private MethodNode mn;
private String argsDesc; private String argsDesc;
private String returnDesc; private String returnDesc;
private String methodName; private String methodName;
private boolean isInterface; private boolean isInterface;
private String instanceCast; private String instanceCast;
private String argsCheckCastDesc; private String argsCheckCastDesc;
private String mName; private String mName;
private String mDesc; private String mDesc;
public Invoker(String methodLoc, String invMethName, String argsDesc, public Invoker(String methodLoc, String invMethName, String argsDesc,
String returnDesc, String methodName) { String returnDesc, String methodName) {
this(methodLoc, methodLoc, invMethName, argsDesc, returnDesc, this(methodLoc, methodLoc, invMethName, argsDesc, returnDesc,
methodName, false, null, null); methodName, false, null, null);
} }
public Invoker(String into, String methodLoc, String invMethName, public Invoker(String into, String methodLoc, String invMethName,
String argsDesc, String returnDesc, String methodName, boolean isInterface, String instanceCast, String argsCheckCastDesc) { String argsDesc, String returnDesc, String methodName, boolean isInterface, String instanceCast, String argsCheckCastDesc) {
this.into = ASMUtils.getClass(into); this.into = ASMUtils.getClass(into);
this.methodLocation = ASMUtils.getClass(methodLoc); this.methodLocation = ASMUtils.getClass(methodLoc);
this.mn = getMethod(this.methodLocation, invMethName, argsDesc); this.mn = getMethod(this.methodLocation, invMethName, argsDesc, returnDesc);
this.returnDesc = returnDesc; this.returnDesc = returnDesc;
this.methodName = methodName; this.methodName = methodName;
this.argsDesc = argsDesc; this.argsDesc = argsDesc;
this.isInterface = isInterface; this.isInterface = isInterface;
this.instanceCast = instanceCast; this.instanceCast = instanceCast;
this.mName = invMethName; this.mName = invMethName;
this.mDesc = argsDesc + returnDesc; this.mDesc = argsDesc + returnDesc;
this.argsCheckCastDesc = argsCheckCastDesc; this.argsCheckCastDesc = argsCheckCastDesc;
} }
private static MethodNode getMethod(ClassNode into, String name, String desc) { private static MethodNode getMethod(ClassNode into, String name, String argsDesc, String returnDesc) {
for (Object m : into.methods) { for (Object method : into.methods) {
MethodNode methodNode = (MethodNode) m; MethodNode m = (MethodNode) method;
String s = methodNode.desc.substring(0, methodNode.desc.indexOf(')') + 1); if (m.name.equals(name) && m.desc.substring(0, m.desc.indexOf(')') + 1).equals(argsDesc)
if (methodNode.name.equals(name) && s.equals(desc)) { && (returnDesc == null || Type.getType(m.desc).getReturnType().getDescriptor().equals(returnDesc))) {
return methodNode; return m;
} }
} }
return null; return null;
} }
/** /**
* Short route for getAdaptar().inject(); * Short route for getAdaptar().inject();
* *
* @see AddInvokerAdapter#inject * @see AddInvokerAdapter#inject
*/ */
@Override @Override
public void inject() { public void inject() {
getAdapter().inject(); getAdapter().inject();
} }
/** /**
* Gets the AddInvokerAdapter * Gets the AddInvokerAdapter
* *
* @return AddInvokerAdapter * @return AddInvokerAdapter
*/ */
public AddInvokerAdapter getAdapter() { public AddInvokerAdapter getAdapter() {
return new AddInvokerAdapter(this.methodLocation, this.into, this.mn, this.mName, this.mDesc, return new AddInvokerAdapter(this.methodLocation, this.into, this.mn, this.mName, this.mDesc,
this.argsDesc, this.returnDesc, this.methodName, this.isInterface, this.instanceCast, this.argsCheckCastDesc); this.argsDesc, this.returnDesc, this.methodName, this.isInterface, this.instanceCast, this.argsCheckCastDesc);
} }
} }
@@ -7,49 +7,49 @@ import org.parabot.core.asm.adapters.AddSetterAdapter;
import org.parabot.core.asm.interfaces.Injectable; import org.parabot.core.asm.interfaces.Injectable;
/** /**
*
* This class is used for injecting a setter for a specific field * This class is used for injecting a setter for a specific field
* *
* @author Everel * @author Everel
*
*/ */
public class Setter implements Injectable { public class Setter implements Injectable {
private ClassNode fieldLocation; private ClassNode fieldLocation;
private ClassNode into; private ClassNode into;
private FieldNode field; private FieldNode field;
private String name; private String name;
private String desc; private String desc;
private boolean methodStatic; private boolean methodStatic;
public Setter(final String fieldLocation, String into, final String fieldName, final String methodName, final String desc, final boolean methodStatic, final String fieldDesc) { public Setter(final String fieldLocation, String into, final String fieldName, final String methodName, final String desc, final boolean methodStatic, final String fieldDesc) {
this.fieldLocation = ASMUtils.getClass(fieldLocation); this.fieldLocation = ASMUtils.getClass(fieldLocation);
into = (into == null) ? fieldLocation : into; into = (into == null) ? fieldLocation : into;
this.into = ASMUtils.getClass(into); this.into = ASMUtils.getClass(into);
this.field = ASMUtils.getField(this.fieldLocation, fieldName, fieldDesc); this.field = ASMUtils.getField(this.fieldLocation, fieldName, fieldDesc);
this.name = methodName; this.name = methodName;
this.desc = (desc == null) ? this.field.desc : desc; this.desc = (desc == null) ? this.field.desc : desc;
this.methodStatic = methodStatic; this.methodStatic = methodStatic;
} }
public Setter(final String fieldLocation, final String fieldName, final String methodName) { public Setter(final String fieldLocation, final String fieldName, final String methodName) {
this(fieldLocation, null, fieldName, methodName, null, false, null); this(fieldLocation, null, fieldName, methodName, null, false, null);
} }
/** /**
* Short route for getAdaptar().inject(); * Short route for getAdaptar().inject();
* @see AddSetterAdapter#inject *
*/ * @see AddSetterAdapter#inject
@Override */
public void inject() { @Override
getAdapter().inject(); public void inject() {
} getAdapter().inject();
}
/** /**
* Gets the AddGetterAdapter * Gets the AddGetterAdapter
* @return AddGetterAdapter *
*/ * @return AddGetterAdapter
public AddSetterAdapter getAdapter() { */
return new AddSetterAdapter(fieldLocation, into, field, name, desc, methodStatic); public AddSetterAdapter getAdapter() {
} return new AddSetterAdapter(fieldLocation, into, field, name, desc, methodStatic);
}
} }
@@ -2,33 +2,32 @@ package org.parabot.core.asm.wrappers;
import org.parabot.core.asm.adapters.AddSuperAdapter; import org.parabot.core.asm.adapters.AddSuperAdapter;
import org.parabot.core.asm.interfaces.Injectable; import org.parabot.core.asm.interfaces.Injectable;
/** /**
*
* This class is used for changing the super class of a class * This class is used for changing the super class of a class
* *
* @author Everel * @author Everel
*
*/ */
public class Super implements Injectable { public class Super implements Injectable {
private String className; private String className;
private String superClassName; private String superClassName;
public Super(String className, String superClassName) { public Super(String className, String superClassName) {
this.className = className; this.className = className;
this.superClassName = superClassName; this.superClassName = superClassName;
} }
/** /**
* Adds a superclass to a class * Adds a superclass to a class
* Short route for getAdapter().inject * Short route for getAdapter().inject
*/ */
@Override @Override
public void inject() { public void inject() {
getAdapter().inject(); getAdapter().inject();
} }
public AddSuperAdapter getAdapter() { public AddSuperAdapter getAdapter() {
return new AddSuperAdapter(className, superClassName); return new AddSuperAdapter(className, superClassName);
} }
} }
@@ -1,11 +1,9 @@
package org.parabot.core.build; package org.parabot.core.build;
/** /**
*
* Class used for adding urls to the buildpath * Class used for adding urls to the buildpath
* *
* @author Everel * @author Everel
*
*/ */
public class BuildPath extends org.parabot.api.io.build.BuildPath { public class BuildPath extends org.parabot.api.io.build.BuildPath {
@@ -1,12 +1,17 @@
package org.parabot.core.classpath; package org.parabot.core.classpath;
import java.io.File; import org.objectweb.asm.ClassReader;
import java.io.FileInputStream; import org.objectweb.asm.ClassWriter;
import java.io.FileNotFoundException; import org.objectweb.asm.commons.RemappingClassAdapter;
import java.io.FileOutputStream; import org.objectweb.asm.tree.ClassNode;
import java.io.IOException; import org.parabot.core.Directories;
import java.io.InputStream; import org.parabot.core.asm.ClassRemapper;
import java.io.OutputStream; import org.parabot.core.asm.RedirectClassAdapter;
import org.parabot.core.build.BuildPath;
import org.parabot.core.io.SizeInputStream;
import org.parabot.core.ui.components.VerboseLoader;
import java.io.*;
import java.net.MalformedURLException; import java.net.MalformedURLException;
import java.net.URL; import java.net.URL;
import java.net.URLConnection; import java.net.URLConnection;
@@ -20,17 +25,6 @@ import java.util.jar.JarOutputStream;
import java.util.zip.ZipEntry; import java.util.zip.ZipEntry;
import java.util.zip.ZipInputStream; import java.util.zip.ZipInputStream;
import org.objectweb.asm.ClassReader;
import org.objectweb.asm.ClassWriter;
import org.objectweb.asm.commons.RemappingClassAdapter;
import org.objectweb.asm.tree.ClassNode;
import org.parabot.core.Directories;
import org.parabot.core.asm.ClassRemapper;
import org.parabot.core.asm.RedirectClassAdapter;
import org.parabot.core.build.BuildPath;
import org.parabot.core.io.SizeInputStream;
import org.parabot.core.ui.components.VerboseLoader;
/** /**
* Manages, parses and dumps class files & jars * Manages, parses and dumps class files & jars
* *
@@ -38,274 +32,274 @@ import org.parabot.core.ui.components.VerboseLoader;
* @author Matt * @author Matt
*/ */
public class ClassPath { public class ClassPath {
public final ArrayList<String> classNames; public final ArrayList<String> classNames;
public final HashMap<String, ClassNode> classes; public final HashMap<String, ClassNode> classes;
public final Map<String, File> resources; public final Map<String, File> resources;
public URL lastParsed; public URL lastParsed;
private ClassRemapper classRemapper; private ClassRemapper classRemapper;
private boolean isJar; private boolean isJar;
private boolean parseJar; private boolean parseJar;
private ArrayList<URL> jarFiles; private ArrayList<URL> jarFiles;
public ClassPath() {
this(false);
}
public ClassPath() { public ClassPath(final boolean isJar) {
this(false); this.classNames = new ArrayList<String>();
} this.classes = new HashMap<String, ClassNode>();
this.resources = new HashMap<String, File>();
this.classRemapper = new ClassRemapper();
this.parseJar = true;
this.jarFiles = new ArrayList<URL>();
this.isJar = isJar;
}
public ClassPath(final boolean isJar) { public void addJar(final File file) {
this.classNames = new ArrayList<String>(); try {
this.classes = new HashMap<String, ClassNode>(); addJar(file.toURI().toURL());
this.resources = new HashMap<String, File>(); } catch (MalformedURLException e) {
this.classRemapper = new ClassRemapper(); e.printStackTrace();
this.parseJar = true; }
this.jarFiles = new ArrayList<URL>(); }
this.isJar = isJar;
}
public void addJar(final File file) { public void addJar(final URL url) {
try { this.lastParsed = url;
addJar(file.toURI().toURL()); try {
} catch (MalformedURLException e) { addJar(url.openConnection());
e.printStackTrace(); } catch (IOException e) {
} e.printStackTrace();
} }
}
public void addJar(final URL url) { /**
this.lastParsed = url; * Adds a jar to this classpath
try { *
addJar(url.openConnection()); * @param connection
} catch (IOException e) { */
e.printStackTrace(); public void addJar(final URLConnection connection) {
} try {
} final int size = connection.getContentLength();
final SizeInputStream sizeInputStream = new SizeInputStream(
connection.getInputStream(), size, VerboseLoader.get());
final ZipInputStream zin = new ZipInputStream(sizeInputStream);
ZipEntry e;
while ((e = zin.getNextEntry()) != null) {
if (e.isDirectory()) {
continue;
}
if (e.getName().endsWith(".class")) {
loadClass(zin);
} else {
loadResource(e.getName(), zin);
}
VerboseLoader.setState("Downloading: " + e.getName());
}
zin.close();
} catch (IOException e) {
e.printStackTrace();
}
VerboseLoader.get().onProgressUpdate(100);
}
/** /**
* Adds a jar to this classpath * Adds a jar to this classpath
* *
* @param connection * @param url - in string format
*/ */
public void addJar(final URLConnection connection) { public void addJar(final String url) {
try { try {
final int size = connection.getContentLength(); addJar(new URL(url));
final SizeInputStream sizeInputStream = new SizeInputStream( } catch (MalformedURLException e) {
connection.getInputStream(), size, VerboseLoader.get()); e.printStackTrace();
final ZipInputStream zin = new ZipInputStream(sizeInputStream); }
ZipEntry e; }
while ((e = zin.getNextEntry()) != null) {
if (e.isDirectory())
continue;
if (e.getName().endsWith(".class")) {
loadClass(zin);
} else {
loadResource(e.getName(), zin);
}
VerboseLoader.setState("Downloading: " + e.getName());
}
zin.close();
} catch (IOException e) {
e.printStackTrace();
}
VerboseLoader.get().onProgressUpdate(100);
}
/**
* Whether jar files should be parsed or ignored
*
* @param enabled
*/
public void parseJarFiles(final boolean enabled) {
this.parseJar = enabled;
}
/**
* Finds and loads all classes/jar files in folder
*
* @param directory
*/
public void addClasses(final File directory) {
if (directory == null || !directory.isDirectory()) {
throw new IllegalArgumentException("Not a valid directory.");
}
addClasses(directory, null);
}
/** /**
* Adds a jar to this classpath * Finds and loads all classes/jar files in folder
* *
* @param url * @param f to find class / jar files
* - in string format * @param root
*/ */
public void addJar(final String url) { public void addClasses(final File f, File root) {
try { if (f == null) {
addJar(new URL(url)); return;
} catch (MalformedURLException e) { }
e.printStackTrace(); if (!f.exists()) {
} f.mkdirs();
} }
if (root == null) {
root = f;
}
for (File f1 : f.listFiles()) {
if (f1 == null) {
continue;
} else if (f1.isDirectory()) {
addClasses(f1, root);
} else {
try (FileInputStream fin = new FileInputStream(f1)) {
if (f1.getName().endsWith(".class")) {
loadClass(fin);
} else if (f.equals(root) && f1.getName().endsWith(".jar")) {
jarFiles.add(f1.toURI().toURL());
if (this.parseJar) {
// if enabled, there may be problem with duplicate
// class names.......
addJar(f1.toURI().toURL());
}
} else {
String path = f1.toURI().relativize(root.toURI())
.getPath();
loadResource(path, fin);
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
/** /**
* Whether jar files should be parsed or ignored * Loads class from input stream
* *
* @param enabled * @param in
*/ *
public void parseJarFiles(final boolean enabled) { * @throws IOException
this.parseJar = enabled;
}
/**
* Finds and loads all classes/jar files in folder
* @param directory
*/
public void addClasses(final File directory) {
if(directory == null || !directory.isDirectory()) {
throw new IllegalArgumentException("Not a valid directory.");
}
addClasses(directory, null);
}
/**
* Finds and loads all classes/jar files in folder
*
* @param f
* to find class / jar files
* @param root
*/
public void addClasses(final File f, File root) {
if (f == null)
return;
if (!f.exists()) {
f.mkdirs();
}
if (root == null) {
root = f;
}
for (File f1 : f.listFiles()) {
if (f1 == null) {
continue;
} else if (f1.isDirectory()) {
addClasses(f1, root);
} else {
try (FileInputStream fin = new FileInputStream(f1)) {
if (f1.getName().endsWith(".class"))
loadClass(fin);
else if (f.equals(root) && f1.getName().endsWith(".jar")) {
jarFiles.add(f1.toURI().toURL());
if (this.parseJar) {
// if enabled, there may be problem with duplicate
// class names.......
addJar(f1.toURI().toURL());
}
} else {
String path = f1.toURI().relativize(root.toURI())
.getPath();
loadResource(path, fin);
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
/**
* Loads class from input stream
*
* @param in
* @throws IOException
*/ */
protected void loadClass(InputStream in) throws IOException { protected void loadClass(InputStream in) throws IOException {
ClassReader cr = new ClassReader(in); ClassReader cr = new ClassReader(in);
ClassNode cn = new ClassNode(); ClassNode cn = new ClassNode();
RemappingClassAdapter rca = new RemappingClassAdapter(cn,classRemapper); RemappingClassAdapter rca = new RemappingClassAdapter(cn, classRemapper);
RedirectClassAdapter redir = new RedirectClassAdapter(rca); RedirectClassAdapter redir = new RedirectClassAdapter(rca);
cr.accept(redir, ClassReader.EXPAND_FRAMES); cr.accept(redir, ClassReader.EXPAND_FRAMES);
classNames.add(cn.name.replace('/', '.')); classNames.add(cn.name.replace('/', '.'));
classes.put(cn.name, cn); classes.put(cn.name, cn);
} }
/**
* Determines if this classpath represents a jar file
*
* @return if this classpath represents a jar file
*/
public boolean isJar() {
return isJar;
}
/**
* Gets all jar files in this classpath
*
* @return array of classpath
*/
public ClassPath[] getJarFiles() {
final ClassPath[] jars = new ClassPath[jarFiles.size()];
for (int i = 0; i < jarFiles.size(); i++) {
final ClassPath classPath = new ClassPath(true);
classPath.addJar(jarFiles.get(i));
jars[i] = classPath;
}
return jars;
}
/** /**
* Determines if this classpath represents a jar file * Dumps a resource from a input stream
* *
* @return if this classpath represents a jar file * @param classPath
*/ * @param name
public boolean isJar() { * @param inputstream
return isJar; *
} * @throws IOException
*/
private void loadResource(final String name, final InputStream in)
throws IOException {
final File f = File.createTempFile("bot", ".tmp",
Directories.getTempDirectory());
f.deleteOnExit();
try (OutputStream out = new FileOutputStream(f)) {
byte[] buffer = new byte[1024];
int len;
while ((len = in.read(buffer)) != -1) {
out.write(buffer, 0, len);
}
} catch (IOException e) {
}
this.resources.put(name, f);
}
/** /**
* Gets all jar files in this classpath * Adds this jar to buildpath
* */
* @return array of classpath public void addToBuildPath() {
*/ BuildPath.add(lastParsed);
public ClassPath[] getJarFiles() { }
final ClassPath[] jars = new ClassPath[jarFiles.size()];
for (int i = 0; i < jarFiles.size(); i++) {
final ClassPath classPath = new ClassPath(true);
classPath.addJar(jarFiles.get(i));
jars[i] = classPath;
}
return jars;
}
/** /**
* Dumps a resource from a input stream * Dump this classPath classes to a jar file
* *
* @param classPath * @param fileName
* @param name */
* @param inputstream public void dump(final String fileName) {
* @throws IOException dump(new File(fileName));
*/ }
private void loadResource(final String name, final InputStream in)
throws IOException {
final File f = File.createTempFile("bot", ".tmp",
Directories.getTempDirectory());
f.deleteOnExit();
try (OutputStream out = new FileOutputStream(f)) {
byte[] buffer = new byte[1024];
int len;
while ((len = in.read(buffer)) != -1)
out.write(buffer, 0, len);
} catch (IOException e) {
}
this.resources.put(name, f);
}
/** /**
* Adds this jar to buildpath * Dump this classPath classes to a jar file
*/ *
public void addToBuildPath() { * @param file
BuildPath.add(lastParsed); */
} public void dump(final File file) {
try {
dump(new FileOutputStream(file));
} catch (FileNotFoundException e) {
e.printStackTrace();
}
}
/** /**
* Dump this classPath classes to a jar file * Dumps this classPath classes to a jar file
* *
* @param fileName * @param stream
*/ */
public void dump(final String fileName) { public void dump(final FileOutputStream stream) {
dump(new File(fileName)); try {
} JarOutputStream out = new JarOutputStream(stream);
for (ClassNode cn : this.classes.values()) {
/** JarEntry je = new JarEntry(cn.name + ".class");
* Dump this classPath classes to a jar file out.putNextEntry(je);
* ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS);
* @param file cn.accept(cw);
*/ out.write(cw.toByteArray());
public void dump(final File file) { }
try { for (Entry<String, File> entry : this.resources.entrySet()) {
dump(new FileOutputStream(file)); JarEntry je = new JarEntry(entry.getKey());
} catch (FileNotFoundException e) { out.putNextEntry(je);
e.printStackTrace(); out.write(Files.readAllBytes(entry.getValue().toPath()));
} }
} out.close();
stream.close();
/** } catch (Exception e) {
* Dumps this classPath classes to a jar file e.printStackTrace();
* @param stream }
*/ }
public void dump(final FileOutputStream stream) {
try {
JarOutputStream out = new JarOutputStream(stream);
for (ClassNode cn : this.classes.values()) {
JarEntry je = new JarEntry(cn.name + ".class");
out.putNextEntry(je);
ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS);
cn.accept(cw);
out.write(cw.toByteArray());
}
for(Entry<String, File> entry : this.resources.entrySet()) {
JarEntry je = new JarEntry(entry.getKey());
out.putNextEntry(je);
out.write(Files.readAllBytes(entry.getValue().toPath()));
}
out.close();
stream.close();
} catch (Exception e) {
e.printStackTrace();
}
}
} }
@@ -4,133 +4,132 @@ package org.parabot.core.desc;
* Holds information about a script * Holds information about a script
* *
* @author Everel * @author Everel
*
*/ */
public class ScriptDescription implements Comparable<ScriptDescription> { public class ScriptDescription implements Comparable<ScriptDescription> {
public String scriptName; public String scriptName;
public String author; public String author;
public String category; public String category;
public double version; public double version;
public String description; public String description;
public String[] servers; public String[] servers;
public String isVip; public String isVip;
public String isPremium; public String isPremium;
public int bdnId; public int bdnId;
/** /**
* The ScriptManifest * The ScriptManifest
* *
* @param scriptName * @param scriptName
* @param author * @param author
* @param category * @param category
* @param version * @param version
* @param description * @param description
* @param servers * @param servers
*/ */
public ScriptDescription(final String scriptName, final String author, public ScriptDescription(final String scriptName, final String author,
final String category, final double version, final String category, final double version,
final String description, final String[] servers) { final String description, final String[] servers) {
this(scriptName, author, category, version, description, servers, null, this(scriptName, author, category, version, description, servers, null,
null, -1); null, -1);
}
/**
* Used for BDN script (see BDNScripts parser)
*
* @param scriptName
* @param author
* @param category
* @param version
* @param description
* @param servers
* @param bdnId
*/
public ScriptDescription(final String scriptName,
final String author, final String category, final double version,
final String description, final String[] servers, final int bdnId) {
this(scriptName, author, category, version, description, servers, null,
null, bdnId);
}
/**
* Used by bot (java scripts and python scripts) and BDN Manager (bdn
* manager is a private program)
*
* @param scriptName
* @param author
* @param category
* @param version
* @param description
* @param servers
* @param vip
* @param premium
*/
public ScriptDescription(final String scriptName, final String author,
final String category, final double version,
final String description, final String[] servers, final String vip,
final String premium) {
this(scriptName, author, category, version, description, servers, vip,
premium, -1);
}
/**
* Main constructor
*
* @param scriptName
* @param author
* @param category
* @param version
* @param description
* @param servers
* @param vip
* @param premium
* @param bdnId
*/
public ScriptDescription(final String scriptName, final String author,
final String category, final double version,
final String description, final String[] servers, final String vip,
final String premium, final int bdnId) {
this.scriptName = scriptName;
this.author = author;
this.category = category;
this.version = version;
this.description = description;
this.servers = servers;
this.isVip = vip;
this.isPremium = premium;
this.bdnId = bdnId;
} }
@Override /**
public String toString() { * Used for BDN script (see BDNScripts parser)
final StringBuilder b = new StringBuilder(); *
b.append("[name: ").append(this.scriptName).append(", author: ") * @param scriptName
.append(this.author).append(", category: ") * @param author
.append(this.category).append(", version: ") * @param category
.append(this.version).append(", description: ") * @param version
.append(this.description).append(", servers: "); * @param description
if(this.servers != null) { * @param servers
for (int i = 0; i < this.servers.length; i++) { * @param bdnId
b.append(this.servers[i]); */
if (i < (this.servers.length - 1)) { public ScriptDescription(final String scriptName,
b.append(" "); final String author, final String category, final double version,
} final String description, final String[] servers, final int bdnId) {
} this(scriptName, author, category, version, description, servers, null,
} null, bdnId);
b.append(", vip: ") }
.append(this.isVip == null ? "unknown" : this.isVip)
.append(", premium: ")
.append(this.isPremium == null ? "unknown" : this.isPremium)
.append(", bdn id: ")
.append(this.bdnId == -1 ? "unknown" : Integer
.toString(this.bdnId))
.append("]");
return b.toString(); /**
} * Used by bot (java scripts and python scripts) and BDN Manager (bdn
* manager is a private program)
*
* @param scriptName
* @param author
* @param category
* @param version
* @param description
* @param servers
* @param vip
* @param premium
*/
public ScriptDescription(final String scriptName, final String author,
final String category, final double version,
final String description, final String[] servers, final String vip,
final String premium) {
this(scriptName, author, category, version, description, servers, vip,
premium, -1);
}
@Override /**
public int compareTo(ScriptDescription o) { * Main constructor
return scriptName.compareTo(o.scriptName); *
} * @param scriptName
* @param author
* @param category
* @param version
* @param description
* @param servers
* @param vip
* @param premium
* @param bdnId
*/
public ScriptDescription(final String scriptName, final String author,
final String category, final double version,
final String description, final String[] servers, final String vip,
final String premium, final int bdnId) {
this.scriptName = scriptName;
this.author = author;
this.category = category;
this.version = version;
this.description = description;
this.servers = servers;
this.isVip = vip;
this.isPremium = premium;
this.bdnId = bdnId;
}
@Override
public String toString() {
final StringBuilder b = new StringBuilder();
b.append("[name: ").append(this.scriptName).append(", author: ")
.append(this.author).append(", category: ")
.append(this.category).append(", version: ")
.append(this.version).append(", description: ")
.append(this.description).append(", servers: ");
if (this.servers != null) {
for (int i = 0; i < this.servers.length; i++) {
b.append(this.servers[i]);
if (i < (this.servers.length - 1)) {
b.append(" ");
}
}
}
b.append(", vip: ")
.append(this.isVip == null ? "unknown" : this.isVip)
.append(", premium: ")
.append(this.isPremium == null ? "unknown" : this.isPremium)
.append(", bdn id: ")
.append(this.bdnId == -1 ? "unknown" : Integer
.toString(this.bdnId))
.append("]");
return b.toString();
}
@Override
public int compareTo(ScriptDescription o) {
return scriptName.compareTo(o.scriptName);
}
} }
@@ -1,45 +1,43 @@
package org.parabot.core.desc; package org.parabot.core.desc;
/** /**
*
* Holds information about a server * Holds information about a server
* *
* @author Everel * @author Everel
*
*/ */
public class ServerDescription implements Comparable<ServerDescription> { public class ServerDescription implements Comparable<ServerDescription> {
private String serverName; private String serverName;
private String author; private String author;
private double revision; private double revision;
public ServerDescription(final String serverName, final String author, public ServerDescription(final String serverName, final String author,
final double revision) { final double revision) {
this.serverName = serverName; this.serverName = serverName;
this.author = author; this.author = author;
this.revision = revision; this.revision = revision;
} }
public String getServerName() { public String getServerName() {
return this.serverName; return this.serverName;
} }
public String getAuthor() { public String getAuthor() {
return this.author; return this.author;
} }
public double getRevision() { public double getRevision() {
return this.revision; return this.revision;
} }
@Override @Override
public String toString() { public String toString() {
return String.format("[Server: %s, Author: %s, Revision: %.2f]", return String.format("[Server: %s, Author: %s, Revision: %.2f]",
this.serverName, this.author, this.revision); this.serverName, this.author, this.revision);
} }
@Override @Override
public int compareTo(ServerDescription o) { public int compareTo(ServerDescription o) {
return this.getServerName().compareTo(o.getServerName()); return this.getServerName().compareTo(o.getServerName());
} }
} }
@@ -1,14 +1,11 @@
package org.parabot.core.desc; package org.parabot.core.desc;
import org.json.simple.JSONObject; import org.json.simple.JSONObject;
import org.json.simple.parser.JSONParser;
import org.json.simple.parser.ParseException; import org.json.simple.parser.ParseException;
import org.parabot.core.Configuration; import org.parabot.core.Configuration;
import org.parabot.core.Core; import org.parabot.core.Core;
import org.parabot.core.ui.utils.UILog;
import org.parabot.environment.api.utils.WebUtil; import org.parabot.environment.api.utils.WebUtil;
import javax.swing.*;
import java.io.BufferedReader; import java.io.BufferedReader;
import java.io.IOException; import java.io.IOException;
import java.net.MalformedURLException; import java.net.MalformedURLException;
@@ -22,92 +19,91 @@ import java.util.zip.CRC32;
* Gets the information for the selected server provider * Gets the information for the selected server provider
* *
* @author Paradox, Everel * @author Paradox, Everel
*
*/ */
public class ServerProviderInfo { public class ServerProviderInfo {
private HashMap<String, Integer> settings; private HashMap<String, Integer> settings;
private Properties properties; private Properties properties;
public ServerProviderInfo(URL providerInfo, String username, String password) { public ServerProviderInfo(URL providerInfo, String username, String password) {
this.properties = new Properties(); this.properties = new Properties();
this.settings = new HashMap<>(); this.settings = new HashMap<>();
try { try {
Core.verbose("Reading info: " + providerInfo); Core.verbose("Reading info: " + providerInfo);
BufferedReader br = WebUtil.getReader(new URL(providerInfo.toString()), username, password); BufferedReader br = WebUtil.getReader(new URL(providerInfo.toString()), username, password);
JSONObject jsonObject = (JSONObject) WebUtil.getJsonParser().parse(br); JSONObject jsonObject = (JSONObject) WebUtil.getJsonParser().parse(br);
for (Object o : jsonObject.entrySet()) { for (Object o : jsonObject.entrySet()) {
Map.Entry<?, ?> pairs = (Map.Entry<?, ?>) o; Map.Entry<?, ?> pairs = (Map.Entry<?, ?>) o;
if (String.valueOf(pairs.getKey()).equalsIgnoreCase("settings")){ if (String.valueOf(pairs.getKey()).equalsIgnoreCase("settings")) {
JSONObject object = (JSONObject) pairs.getValue(); JSONObject object = (JSONObject) pairs.getValue();
parseSettings(object); parseSettings(object);
}else { } else {
properties.put(String.valueOf(pairs.getKey()), String.valueOf(pairs.getValue())); properties.put(String.valueOf(pairs.getKey()), String.valueOf(pairs.getValue()));
} }
} }
if (br != null) { if (br != null) {
br.close(); br.close();
} }
} catch (Exception e) { } catch (Exception e) {
e.printStackTrace(); e.printStackTrace();
} }
} }
public ServerProviderInfo(String clientJar, String hooks, String name, String clientClass, int bankTabs){ public ServerProviderInfo(String clientJar, String hooks, String name, String clientClass, int bankTabs) {
this.properties = new Properties(); this.properties = new Properties();
this.settings = new HashMap<>(); this.settings = new HashMap<>();
try { try {
BufferedReader br = WebUtil.getReader(new URL(Configuration.GET_SERVER_SETTINGS)); BufferedReader br = WebUtil.getReader(new URL(Configuration.GET_SERVER_SETTINGS));
JSONObject settings = (JSONObject) WebUtil.getJsonParser().parse(br); JSONObject settings = (JSONObject) WebUtil.getJsonParser().parse(br);
parseSettings(settings); parseSettings(settings);
} catch (ParseException | IOException e) { } catch (ParseException | IOException e) {
e.printStackTrace(); e.printStackTrace();
} }
this.properties.setProperty("client_jar", clientJar); this.properties.setProperty("client_jar", clientJar);
this.properties.setProperty("hooks", hooks); this.properties.setProperty("hooks", hooks);
this.properties.setProperty("name", name); this.properties.setProperty("name", name);
this.properties.setProperty("client_class", clientClass); this.properties.setProperty("client_class", clientClass);
this.properties.setProperty("provider_crc32", String.valueOf(getCRC32(name, "provider"))); this.properties.setProperty("provider_crc32", String.valueOf(getCRC32(name, "provider")));
this.properties.setProperty("client_crc32", String.valueOf(getCRC32(name, "client"))); this.properties.setProperty("client_crc32", String.valueOf(getCRC32(name, "client")));
this.properties.setProperty("bank_tabs", String.valueOf(bankTabs)); this.properties.setProperty("bank_tabs", String.valueOf(bankTabs));
} }
private long getCRC32(String name, String type){ private long getCRC32(String name, String type) {
CRC32 crc = new CRC32(); CRC32 crc = new CRC32();
name += "-" + type; name += "-" + type;
crc.update(name.getBytes()); crc.update(name.getBytes());
return crc.getValue(); return crc.getValue();
} }
private void parseSettings(JSONObject object){ private void parseSettings(JSONObject object) {
for (Object settingObject : object.entrySet()){ for (Object settingObject : object.entrySet()) {
Map.Entry<?, ?> settingValue = (Map.Entry<?, ?>) settingObject; Map.Entry<?, ?> settingValue = (Map.Entry<?, ?>) settingObject;
String key = (String) settingValue.getKey(); String key = (String) settingValue.getKey();
long value = (Long) settingValue.getValue(); long value = (Long) settingValue.getValue();
settings.put(key, (int) value); settings.put(key, (int) value);
} }
} }
public URL getClient() { public URL getClient() {
try { try {
return new URL(properties.getProperty("client_jar")); return new URL(properties.getProperty("client_jar"));
} catch (MalformedURLException e) { } catch (MalformedURLException e) {
e.printStackTrace(); e.printStackTrace();
} }
return null; return null;
} }
public URL getExtendedHookFile() { public URL getExtendedHookFile() {
try { try {
return new URL(properties.getProperty("hooks") /*+ "&extended=true"*/); return new URL(properties.getProperty("hooks") /*+ "&extended=true"*/);
} catch (MalformedURLException e) { } catch (MalformedURLException e) {
e.printStackTrace(); e.printStackTrace();
return getHookFile(); return getHookFile();
} }
} }
public URL getHookFile() { public URL getHookFile() {
try { try {
@@ -118,31 +114,31 @@ public class ServerProviderInfo {
return null; return null;
} }
public String getClientClass() { public String getClientClass() {
return properties.getProperty("client_class"); return properties.getProperty("client_class");
} }
public String getServerName() { public String getServerName() {
return properties.getProperty("name"); return properties.getProperty("name");
} }
public long getCRC32() { public long getCRC32() {
return Long.parseLong(properties.getProperty("provider_crc32")); return Long.parseLong(properties.getProperty("provider_crc32"));
} }
public long getClientCRC32() { public long getClientCRC32() {
return Long.parseLong(properties.getProperty("client_crc32")); return Long.parseLong(properties.getProperty("client_crc32"));
} }
public int getBankTabs() { public int getBankTabs() {
return Integer.parseInt(properties.getProperty("bank_tabs")); return Integer.parseInt(properties.getProperty("bank_tabs"));
} }
public Properties getProperties() { public Properties getProperties() {
return this.properties; return this.properties;
} }
public HashMap<String, Integer> getSettings() { public HashMap<String, Integer> getSettings() {
return settings; return settings;
} }
} }
@@ -1,33 +1,28 @@
package org.parabot.core.forum; package org.parabot.core.forum;
import org.parabot.core.Core;
import java.io.UnsupportedEncodingException; import java.io.UnsupportedEncodingException;
import java.net.URLEncoder; import java.net.URLEncoder;
/** /**
*
* Class which holds parabot forum account user and pass, only specific classes * Class which holds parabot forum account user and pass, only specific classes
* have access to it unless it's a modified version of parabot intended to * have access to it unless it's a modified version of parabot intended to
* steal user information. * steal user information.
* *
* @author Everel * @author Everel
*
*/ */
public class Account { public class Account {
private String username; private String username;
private String password; private String password;
private String api; private String api;
/** /**
* * @param username - Forum account username
* @param username - Forum account username * @param password - Forum account password
* @param password - Forum account password */
*/ public Account(final String username, final String password) {
public Account(final String username, final String password) { this.username = username;
this.username = username; this.password = password;
this.password = password; }
}
public Account(String username, String password, String api) { public Account(String username, String password, String api) {
this.username = username; this.username = username;
@@ -36,26 +31,29 @@ public class Account {
} }
/** /**
* Gets user's parabot account name * Gets user's parabot account name
* @return username. *
*/ * @return username.
public String getUsername() { */
return this.username; public String getUsername() {
} return this.username;
}
/** /**
* Gets user's parabot password * Gets user's parabot password
* @return password. *
*/ * @return password.
public String getPassword() { */
return this.password; public String getPassword() {
} return this.password;
}
/** /**
* Gets user's parabot account name * Gets user's parabot account name
*
* @return username, already URL UTF-8 encoded. * @return username, already URL UTF-8 encoded.
*/ */
public String getURLUsername(){ public String getURLUsername() {
try { try {
return URLEncoder.encode(this.username, "UTF-8"); return URLEncoder.encode(this.username, "UTF-8");
} catch (UnsupportedEncodingException e) { } catch (UnsupportedEncodingException e) {
@@ -66,9 +64,10 @@ public class Account {
/** /**
* Gets user's password * Gets user's password
*
* @return password, already URL UTF-8 encoded. * @return password, already URL UTF-8 encoded.
*/ */
public String getURLPassword(){ public String getURLPassword() {
try { try {
return URLEncoder.encode(this.password, "UTF-8"); return URLEncoder.encode(this.password, "UTF-8");
} catch (UnsupportedEncodingException e) { } catch (UnsupportedEncodingException e) {
@@ -22,97 +22,96 @@ import java.util.ArrayList;
* Handles logging in to parabot forum, only certain classes may use this class. * Handles logging in to parabot forum, only certain classes may use this class.
* *
* @author Everel * @author Everel
*
*/ */
public final class AccountManager { public final class AccountManager {
private static boolean validated; private static boolean validated;
private static AccountManager instance; private static AccountManager instance;
private Account account; private Account account;
private AccountManager() { private AccountManager() {
} }
public static final void validate() { public static final void validate() {
if (validated) { if (validated) {
return; return;
} }
validated = true; validated = true;
instance = new AccountManager(); instance = new AccountManager();
Core.verbose("Initializing account manager accessors..."); Core.verbose("Initializing account manager accessors...");
final ArrayList<AccountManagerAccess> accessors = new ArrayList<AccountManagerAccess>(); final ArrayList<AccountManagerAccess> accessors = new ArrayList<AccountManagerAccess>();
accessors.add(BDNScripts.MANAGER_FETCHER); accessors.add(BDNScripts.MANAGER_FETCHER);
accessors.add(VerboseLoader.MANAGER_FETCHER); accessors.add(VerboseLoader.MANAGER_FETCHER);
accessors.add(BDNScriptsExecuter.MANAGER_FETCHER); accessors.add(BDNScriptsExecuter.MANAGER_FETCHER);
accessors.add(PublicServers.MANAGER_FETCHER); accessors.add(PublicServers.MANAGER_FETCHER);
accessors.add(PublicServerExecuter.MANAGER_FETCHER); accessors.add(PublicServerExecuter.MANAGER_FETCHER);
accessors.add(PBPreferences.MANAGER_FETCHER); accessors.add(PBPreferences.MANAGER_FETCHER);
for (final AccountManagerAccess accessor : accessors) { for (final AccountManagerAccess accessor : accessors) {
accessor.setManager(instance); accessor.setManager(instance);
} }
Core.verbose("Account managers initialized."); Core.verbose("Account managers initialized.");
} }
public final boolean isLoggedIn() { public final boolean isLoggedIn() {
return account != null; return account != null;
} }
public final Account getAccount() { public final Account getAccount() {
return account; return account;
} }
public final boolean login(final String user, final String pass, boolean requestTwoStep) { public final boolean login(final String user, final String pass, boolean requestTwoStep) {
if (account != null) { if (account != null) {
throw new IllegalStateException("Already logged in."); throw new IllegalStateException("Already logged in.");
} }
JSONObject result = null; JSONObject result = null;
if (!requestTwoStep){ if (!requestTwoStep) {
try { try {
BufferedReader contents = WebUtil.getReader(WebUtil.getConnection( BufferedReader contents = WebUtil.getReader(WebUtil.getConnection(
new URL(Configuration.LOGIN_SERVER), new URL(Configuration.LOGIN_SERVER),
URLEncoder.encode(user, "UTF-8"), URLEncoder.encode(user, "UTF-8"),
URLEncoder.encode(pass, "UTF-8"))); URLEncoder.encode(pass, "UTF-8")));
result = (JSONObject) WebUtil.getJsonParser().parse(contents); result = (JSONObject) WebUtil.getJsonParser().parse(contents);
} catch (Throwable t) { } catch (Throwable t) {
t.printStackTrace(); t.printStackTrace();
return false; return false;
} }
}else{ } else {
try { try {
String two = JOptionPane.showInputDialog("Please provide your two factor authentication code\nYou can find this in either your email or the app you've setup"); String two = JOptionPane.showInputDialog("Please provide your two factor authentication code\nYou can find this in either your email or the app you've setup");
if (two != null && two.length() > 0) { if (two != null && two.length() > 0) {
String contents = WebUtil.getContents(Configuration.LOGIN_SERVER, String contents = WebUtil.getContents(Configuration.LOGIN_SERVER,
"username=" + URLEncoder.encode(user, "UTF-8") + "&password=" + URLEncoder.encode(pass, "UTF-8") + "&2fa=" + URLEncoder.encode(two, "UTF-8") "username=" + URLEncoder.encode(user, "UTF-8") + "&password=" + URLEncoder.encode(pass, "UTF-8") + "&2fa=" + URLEncoder.encode(two, "UTF-8")
); );
result = (JSONObject) WebUtil.getJsonParser().parse(contents); result = (JSONObject) WebUtil.getJsonParser().parse(contents);
} }
} catch (Throwable t) { } catch (Throwable t) {
t.printStackTrace(); t.printStackTrace();
return false; return false;
} }
} }
if (result != null) { if (result != null) {
if (result.get("complete") != null) { if (result.get("complete") != null) {
String api = (String) ((JSONObject) result.get("data")).get("api"); String api = (String) ((JSONObject) result.get("data")).get("api");
account = new Account(user, pass, api); account = new Account(user, pass, api);
Context.setUsername(user); Context.setUsername(user);
return true; return true;
} else if (result.get("error") != null) { } else if (result.get("error") != null) {
String errorResult = (String) result.get("error"); String errorResult = (String) result.get("error");
if (errorResult.equals("2fa") || errorResult.equals("2fae")) { if (errorResult.equals("2fa") || errorResult.equals("2fae")) {
return login(user, pass, true); return login(user, pass, true);
} }
Core.verbose(errorResult); Core.verbose(errorResult);
return false; return false;
} }
} }
return false; return false;
} }
} }
@@ -1,14 +1,12 @@
package org.parabot.core.forum; package org.parabot.core.forum;
/** /**
*
* Gives access to account details * Gives access to account details
* *
* @author Everel * @author Everel
*
*/ */
public interface AccountManagerAccess { public interface AccountManagerAccess {
public void setManager(AccountManager manager); public void setManager(AccountManager manager);
} }
@@ -1,12 +1,10 @@
package org.parabot.core.io; package org.parabot.core.io;
/** /**
*
* Keeps track of a progress * Keeps track of a progress
* *
* @author Everel * @author Everel
*
*/ */
public interface ProgressListener extends org.parabot.api.io.ProgressListener{ public interface ProgressListener extends org.parabot.api.io.ProgressListener {
} }
@@ -4,61 +4,59 @@ import java.io.IOException;
import java.io.InputStream; import java.io.InputStream;
/** /**
*
* @author Everel * @author Everel
*
*/ */
public class SizeInputStream extends InputStream { public class SizeInputStream extends InputStream {
public int bytesRead; public int bytesRead;
private ProgressListener l; private ProgressListener l;
private InputStream in; private InputStream in;
private long startTime; private long startTime;
private double size; private double size;
public SizeInputStream(InputStream in, int size, ProgressListener l) { public SizeInputStream(InputStream in, int size, ProgressListener l) {
this.in = in; this.in = in;
this.size = size; this.size = size;
this.l = l; this.l = l;
this.startTime = System.currentTimeMillis(); this.startTime = System.currentTimeMillis();
} }
public int available() { public int available() {
return ((int) size - bytesRead); return ((int) size - bytesRead);
} }
public int read() throws IOException { public int read() throws IOException {
int b = in.read(); int b = in.read();
if (b != -1) { if (b != -1) {
bytesRead++; bytesRead++;
} }
updateListener(); updateListener();
return b; return b;
} }
public int read(byte[] b) throws IOException { public int read(byte[] b) throws IOException {
int read = in.read(b); int read = in.read(b);
bytesRead += read; bytesRead += read;
updateListener(); updateListener();
return read; return read;
} }
public int read(byte[] b, int off, int len) throws IOException { public int read(byte[] b, int off, int len) throws IOException {
int read = in.read(b, off, len); int read = in.read(b, off, len);
bytesRead += read; bytesRead += read;
updateListener(); updateListener();
return read; return read;
} }
private void updateListener() { private void updateListener() {
if(l != null) { if (l != null) {
double percent = ( bytesRead / size) * 100.0D; double percent = (bytesRead / size) * 100.0D;
l.onProgressUpdate(percent); l.onProgressUpdate(percent);
long curTime = System.currentTimeMillis(); long curTime = System.currentTimeMillis();
double timeSeconds = (curTime - startTime) / 1000.0D; double timeSeconds = (curTime - startTime) / 1000.0D;
double speed = bytesRead / (1024.0D * 1024.0D) / timeSeconds; double speed = bytesRead / (1024.0D * 1024.0D) / timeSeconds;
l.updateDownloadSpeed(speed); l.updateDownloadSpeed(speed);
} }
} }
} }
@@ -1,9 +1,7 @@
package org.parabot.core.lib; package org.parabot.core.lib;
/** /**
*
* @author Everel * @author Everel
*
*/ */
public abstract class Library extends org.parabot.api.io.libraries.Library { public abstract class Library extends org.parabot.api.io.libraries.Library {
@@ -1,76 +1,74 @@
package org.parabot.core.lib.javafx; package org.parabot.core.lib.javafx;
import java.io.File;
import java.net.URL;
import org.parabot.core.Core; import org.parabot.core.Core;
import org.parabot.core.Directories; import org.parabot.core.Directories;
import org.parabot.core.build.BuildPath; import org.parabot.core.build.BuildPath;
import org.parabot.core.lib.Library; import org.parabot.core.lib.Library;
import org.parabot.environment.api.utils.JavaUtil; import org.parabot.environment.api.utils.JavaUtil;
import java.io.File;
import java.net.URL;
/** /**
*
* Jython util class * Jython util class
* *
* @author Everel * @author Everel
*
*/ */
public class JavaFX extends Library { public class JavaFX extends Library {
private static boolean valid; private static boolean valid;
@Override public static boolean isValid() {
public void init() { return valid;
if (!hasJar()) { }
System.err.println("Failed to load javafx... [jar missing]");
return;
}
Core.verbose("Adding javafx jar file to build path: "
+ getJarFileURL().getPath());
BuildPath.add(getJarFileURL());
try { @Override
Class.forName("javafx.application.Application"); public void init() {
valid = true; if (!hasJar()) {
} catch (ClassNotFoundException e) { System.err.println("Failed to load javafx... [jar missing]");
System.err return;
.println("Failed to add javafx to build path, or incorrupt download"); }
} Core.verbose("Adding javafx jar file to build path: "
+ getJarFileURL().getPath());
BuildPath.add(getJarFileURL());
Core.verbose("JavaFX initialized."); try {
} Class.forName("javafx.application.Application");
valid = true;
} catch (ClassNotFoundException e) {
System.err
.println("Failed to add javafx to build path, or incorrupt download");
}
@Override Core.verbose("JavaFX initialized.");
public boolean isAdded() { }
return valid;
}
@Override @Override
public File getJarFile() { public boolean isAdded() {
return new File(Directories.getCachePath(), "javafx.jar"); return valid;
} }
@Override @Override
public URL getDownloadLink() { public File getJarFile() {
try { return new File(Directories.getCachePath(), "javafx.jar");
return new URL("http://bot.parabot.org/libs/jfxrt.jar"); }
} catch (Throwable t) {
t.printStackTrace();
}
return null;
}
@Override @Override
public boolean requiresJar() { public URL getDownloadLink() {
return JavaUtil.JAVA_VERSION <= 1.7; try {
} return new URL("http://bot.parabot.org/libs/jfxrt.jar");
} catch (Throwable t) {
t.printStackTrace();
}
return null;
}
@Override @Override
public String getLibraryName() { public boolean requiresJar() {
return "JavaFX"; return JavaUtil.JAVA_VERSION <= 1.7;
} }
public static boolean isValid() { @Override
return valid; public String getLibraryName() {
} return "JavaFX";
}
} }
@@ -7,71 +7,75 @@ import java.util.Enumeration;
import java.util.NoSuchElementException; import java.util.NoSuchElementException;
public class NetworkInterface { public class NetworkInterface {
public static byte[] mac = new byte[] { 11, 11, 11, 11, 11, 11 }; public static byte[] mac = new byte[]{ 11, 11, 11, 11, 11, 11 };
private static byte[] realMac; private static byte[] realMac;
private static NetworkInterface cached; private static NetworkInterface cached;
static { static {
try { try {
mac = getRealHardwareAddress(); mac = getRealHardwareAddress();
} catch (SocketException ignored) { } catch (SocketException ignored) {
} }
} }
public byte[] getHardwareAddress() { public static Enumeration<NetworkInterface> getNetworkInterfaces()
return mac; throws SocketException {
} final ArrayList<NetworkInterface> netifs = new ArrayList<>();
public static Enumeration<NetworkInterface> getNetworkInterfaces() return new Enumeration<NetworkInterface>() {
throws SocketException { private int i = 0;
final ArrayList<NetworkInterface> netifs = new ArrayList<>();
return new Enumeration<NetworkInterface>() { public NetworkInterface nextElement() {
private int i = 0; if (i < netifs.size()) {
public NetworkInterface nextElement() { NetworkInterface netif = netifs.get(i++);
if (i < netifs.size()) { return netif;
NetworkInterface netif = netifs.get(i++); } else {
return netif; throw new NoSuchElementException();
} else { }
throw new NoSuchElementException(); }
}
}
public boolean hasMoreElements() { public boolean hasMoreElements() {
return (i < netifs.size()); return (i < netifs.size());
} }
}; };
} }
public static byte[] getRealHardwareAddress() throws SocketException{ public static byte[] getRealHardwareAddress() throws SocketException {
if (realMac != null) if (realMac != null) {
return realMac; return realMac;
try { }
return realMac = java.net.NetworkInterface.getByInetAddress( try {
InetAddress.getLocalHost()).getHardwareAddress(); return realMac = java.net.NetworkInterface.getByInetAddress(
} catch (Exception ignored) { InetAddress.getLocalHost()).getHardwareAddress();
} } catch (Exception ignored) {
return mac; }
} return mac;
}
public static NetworkInterface getByInetAddress(InetAddress addr) { public static NetworkInterface getByInetAddress(InetAddress addr) {
if (cached == null) if (cached == null) {
cached = new NetworkInterface(); cached = new NetworkInterface();
return cached; }
} return cached;
}
public static void setMac(byte[] mac2) { public static void setMac(byte[] mac2) {
System.out.println("Setting mac address to: " + formatMac(mac2)); System.out.println("Setting mac address to: " + formatMac(mac2));
mac = mac2; mac = mac2;
} }
public static String formatMac(byte[] mac){ public static String formatMac(byte[] mac) {
StringBuilder b = new StringBuilder(); StringBuilder b = new StringBuilder();
for(int i = 0; i < 6;i++){ for (int i = 0; i < 6; i++) {
b.append(String.format("%02X", mac[i])); b.append(String.format("%02X", mac[i]));
if(i < 5) if (i < 5) {
b.append(':'); b.append(':');
} }
return b.toString(); }
} return b.toString();
}
public byte[] getHardwareAddress() {
return mac;
}
} }
@@ -4,63 +4,62 @@ import java.io.IOException;
public class Runtime { public class Runtime {
private java.lang.Runtime rt; private static Runtime cached;
private java.lang.Runtime rt;
private static Runtime cached; private Runtime(java.lang.Runtime rt) {
this.rt = rt;
}
private Runtime(java.lang.Runtime rt){ public static Runtime getRuntime() {
this.rt = rt; if (cached == null) {
} cached = new Runtime(java.lang.Runtime.getRuntime());
}
return cached;
}
public void addShutdownHook(Thread t) {
rt.addShutdownHook(t);
}
public void addShutdownHook(Thread t){ public int availableProcessors() {
rt.addShutdownHook(t); return rt.availableProcessors();
} }
public int availableProcessors(){ public void exit(int i) {
return rt.availableProcessors(); rt.exit(i);
} }
public void exit(int i){ public Process exec(String str) throws IOException {
rt.exit(i); System.out.println("RT:" + str);
} System.out.println("RT:" + str);
return rt.exec(str);
}
public Process exec(String str) throws IOException{ public Process exec(String[] cmdarray) throws IOException {
System.out.println("RT:" + str); StringBuffer sb = new StringBuffer();
System.out.println("RT:" + str); for (int i = 0; i < cmdarray.length; i++) {
return rt.exec(str); sb.append(cmdarray[i] + (i < cmdarray.length - 1 ? "," : ""));
} }
System.out.println("RT: {" + sb + "}");
System.out.println("RT: {" + sb + "}");
return rt.exec(cmdarray);
}
public Process exec(String[] cmdarray) throws IOException{ public long freeMemory() {
StringBuffer sb = new StringBuffer(); return rt.freeMemory();
for(int i = 0; i < cmdarray.length;i++){ }
sb.append(cmdarray[i] + (i < cmdarray.length - 1 ? "," : ""));
}
System.out.println("RT: {" + sb + "}");
System.out.println("RT: {" + sb + "}");
return rt.exec(cmdarray);
}
public long freeMemory() { public long totalMemory() {
return rt.freeMemory(); return rt.totalMemory();
} }
public long totalMemory() { public void gc() {
return rt.totalMemory(); rt.gc();
} }
public void gc(){ public long maxMemory() {
rt.gc(); return rt.maxMemory();
} }
public long maxMemory(){
return rt.maxMemory();
}
public static Runtime getRuntime(){
if(cached == null)
cached = new Runtime(java.lang.Runtime.getRuntime());
return cached;
}
} }
@@ -11,284 +11,299 @@ import java.util.List;
public class ProxySocket extends Socket { public class ProxySocket extends Socket {
private static List<ProxySocket> connections = new ArrayList<ProxySocket>(); public static boolean auth = false;
private static List<ProxySocket> connections = new ArrayList<ProxySocket>();
private static ProxyType proxyType = ProxyType.NONE;
private static int proxyPort = 0;
private static String username = null, password = null;
private static InetAddress proxyInetAddress = null;
private InetAddress addr;
private int port;
private InetSocketAddress cachedAddr;
private static ProxyType proxyType = ProxyType.NONE; public ProxySocket(InetAddress addr, int port) throws IOException {
super(addr, port);
}
private static int proxyPort = 0; public ProxySocket() {
super();
}
private InetAddress addr; public ProxySocket(String host, int port) throws IOException {
private int port; super(host, port);
}
private static String username = null, password = null; public static int closeConnections() {
int value = 0;
for (ProxySocket socket : connections) {
try {
connections.remove(socket);
if (socket.isClosed()) {
continue;
}
socket.close();
value++;
} catch (Exception e) {
public static boolean auth = false; }
}
return value;
}
private static InetAddress proxyInetAddress = null; public static void setProxy(ProxyType type, String host, int port) {
try {
proxyInetAddress = InetAddress.getByName(host);
proxyPort = port;
proxyType = type;
} catch (UnknownHostException e) {
throw new RuntimeException(e);
}
}
private InetSocketAddress cachedAddr; public static InetAddress getProxyAddress() {
return proxyInetAddress;
}
public static int closeConnections() { public static int getProxyPort() {
int value = 0; return proxyPort;
for (ProxySocket socket : connections) }
try {
connections.remove(socket);
if (socket.isClosed())
continue;
socket.close();
value++;
} catch (Exception e) {
} public static ProxyType getProxyType() {
return value; return proxyType;
} }
public ProxySocket(InetAddress addr, int port) throws IOException { public static void setType(ProxyType pt) {
super(addr, port); proxyType = pt;
} }
public ProxySocket() { public static int getConnectionCount() {
super(); return connections.size();
} }
public ProxySocket(String host, int port) throws IOException { public static void setLogin(String user, char[] pass) {
super(host, port); setLogin(user, new String(pass));
} }
public static void setProxy(ProxyType type, String host, int port) { public static void setLogin(String user, String pass) {
try { username = user;
proxyInetAddress = InetAddress.getByName(host); password = pass;
proxyPort = port; }
proxyType = type;
} catch (UnknownHostException e) {
throw new RuntimeException(e);
}
}
public static InetAddress getProxyAddress() { @Override
return proxyInetAddress; public void connect(SocketAddress addr) throws IOException {
} connections.add(this);
if (addr instanceof InetSocketAddress) {
InetSocketAddress isa = (InetSocketAddress) addr;
this.addr = InetAddress.getByName(isa.getHostString());
this.port = isa.getPort();
}
if (proxyType != ProxyType.NONE) {
try {
super.connect(cachedAddr = new InetSocketAddress(
proxyInetAddress, proxyPort));
initProxy();
} catch (Exception e) {
UILog.log("Proxy Error", e.getMessage(),
JOptionPane.ERROR_MESSAGE);
}
} else {
super.connect(addr);
}
}
public static int getProxyPort() { private void initProxy() throws IOException {
return proxyPort; System.out.println("Proxying:" + addr + ":" + port + " Over:"
} + proxyInetAddress + ":" + proxyPort + " Type:" + proxyType);
switch (proxyType) {
case HTTP:
http_connect();
break;
case SOCKS4:
socks4_connect();
break;
case SOCKS5:
socks5_connect();
break;
default:
throw new IOException("Unsupported proxy type:" + proxyType);
}
}
public static ProxyType getProxyType() { private void http_connect() throws IOException {
return proxyType; InputStream in = getInputStream();
} BufferedReader br = new BufferedReader(new InputStreamReader(in));
OutputStream out = getOutputStream();
out.write(("CONNECT " + addr.getHostAddress() + ":" + port + "\r\n")
.getBytes());
// out.write("Connection:keep-alive\r\n".getBytes());
out.write("\r\n".getBytes());
String str;
while ((str = br.readLine()) != null) {
if (str.length() == 0) {
break;
}
if (!str.startsWith("HTTP")) {
continue;
}
int code = Integer.parseInt(str.substring(9, 12));
switch (code) {
case 404:
throw new IOException(
"Proxy seems to think we're connecting to a webpage...");
case 403:
throw new IOException(
"Proxy doesn't support connecting to port: " + port
+ "! Try a different proxy.");
}
if (code / 100 != 2) {
throw new IOException(
"Unable to connect to proxy server! HTTP Error code:"
+ code);
}
}
}
@Override private void socks4_connect() throws IOException {
public void connect(SocketAddress addr) throws IOException { DataOutputStream out = new DataOutputStream(getOutputStream());
connections.add(this); DataInputStream in = new DataInputStream(getInputStream());
if (addr instanceof InetSocketAddress) {
InetSocketAddress isa = (InetSocketAddress) addr;
this.addr = InetAddress.getByName(isa.getHostString());
this.port = isa.getPort();
}
if (proxyType != ProxyType.NONE) {
try {
super.connect(cachedAddr = new InetSocketAddress(
proxyInetAddress, proxyPort));
initProxy();
} catch (Exception e) {
UILog.log("Proxy Error", e.getMessage(),
JOptionPane.ERROR_MESSAGE);
}
} else
super.connect(addr);
}
private void initProxy() throws IOException { out.write(0x04);
System.out.println("Proxying:" + addr + ":" + port + " Over:" out.write(0x01); // connection type (TCP stream)
+ proxyInetAddress + ":" + proxyPort + " Type:" + proxyType); out.writeShort(port);
switch (proxyType) { byte[] b = addr.getAddress();
case HTTP: if (b.length != 4) {
http_connect(); throw new IOException("Unsupported IP type for socksv4!");
break; }
case SOCKS4: out.write(b);
socks4_connect(); out.write(0); // the userID stuff, 0 means end of string (null
break; // terminated)
case SOCKS5: out.flush();
socks5_connect();
break;
default:
throw new IOException("Unsupported proxy type:" + proxyType);
}
}
private void http_connect() throws IOException { if (in.read() != 0x00) // null byte
InputStream in = getInputStream(); {
BufferedReader br = new BufferedReader(new InputStreamReader(in)); throw new IOException("Proxy server dun goofed");
OutputStream out = getOutputStream(); }
out.write(("CONNECT " + addr.getHostAddress() + ":" + port + "\r\n") if (in.read() != 0x5a) {
.getBytes()); throw new IOException(
// out.write("Connection:keep-alive\r\n".getBytes()); "Proxy server was unable to connect to server!");
out.write("\r\n".getBytes()); }
String str;
while ((str = br.readLine()) != null) {
if (str.length() == 0)
break;
if (!str.startsWith("HTTP"))
continue;
int code = Integer.parseInt(str.substring(9, 12));
switch (code) {
case 404:
throw new IOException(
"Proxy seems to think we're connecting to a webpage...");
case 403:
throw new IOException(
"Proxy doesn't support connecting to port: " + port
+ "! Try a different proxy.");
}
if (code / 100 != 2)
throw new IOException(
"Unable to connect to proxy server! HTTP Error code:"
+ code);
}
}
private void socks4_connect() throws IOException { in.readShort(); // ignored
DataOutputStream out = new DataOutputStream(getOutputStream()); in.readFully(b); // ignored
DataInputStream in = new DataInputStream(getInputStream()); }
out.write(0x04); private void socks5_connect() throws IOException {
out.write(0x01); // connection type (TCP stream) DataOutputStream out = new DataOutputStream(getOutputStream());
out.writeShort(port); DataInputStream in = new DataInputStream(getInputStream());
byte[] b = addr.getAddress(); out.write(0x05); // the version
if (b.length != 4) out.write(auth ? 2 : 1); // number of authentication methods (no auth
throw new IOException("Unsupported IP type for socksv4!"); // for now)
out.write(b); out.write(0); // the authentication (none)
out.write(0); // the userID stuff, 0 means end of string (null if (auth) {
// terminated) out.write(2);
out.flush(); }
out.flush();
if (in.read() != 0x05) // remote proxy version
{
throw new IOException("Proxy server is not supported!");
}
switch (in.read()) { // auth method
case 0:
break; // no auth
case 2:
// username and pass stuff
out.write(0x01); // user/pass version #
out.write(username.length());
out.write(username.getBytes());
out.write(password.length());
out.write(password.getBytes());
out.flush();
in.read(); // skip the version
if (in.read() == 0) // Successful login, continue
{
break;
}
default:
throw new IOException("Proxy server declined request!");
}
if (in.read() != 0x00) // null byte // now to write the actual request
throw new IOException("Proxy server dun goofed"); out.write(0x05); // again the socks version
if (in.read() != 0x5a) out.write(0x01); // the connection type (0x01 = TCP Connection)
throw new IOException( out.write(0x00); // the reserve byte, un-used
"Proxy server was unable to connect to server!"); byte[] b = addr.getAddress();
out.write(b.length == 4 ? 0x01 : 0x04); // if ipv4 or ipv6 (0x03 =
// domain name, but that's
// unsupported as of yet)
out.write(b);
out.writeShort(port);
out.flush();
in.readShort(); // ignored // now to read the server's reply
in.readFully(b); // ignored if (in.read() != 0x05) // socks version (again)
} {
throw new IOException("Proxy server dun goofed");
}
int reply = in.read();
if (reply == 0x08) {
throw new IOException("Bad address sent to proxy server");
}
if (reply != 0x00) {
throw new IOException("Unable to connect to server!");
}
in.read(); // reserve byte
int addrType = in.read();
b = new byte[4];
switch (addrType) {
case 0x01:
b = new byte[4];
break;
case 0x04:
b = new byte[16];
break;
default:
throw new IOException("Bad address type from proxy server!");
}
in.readFully(b);
in.readShort(); // the returned port #, ignored
}
private void socks5_connect() throws IOException { @Override
DataOutputStream out = new DataOutputStream(getOutputStream()); public int getPort() {
DataInputStream in = new DataInputStream(getInputStream()); if (super.getInetAddress().equals(proxyInetAddress)) {
out.write(0x05); // the version return port;
out.write(auth ? 2 : 1); // number of authentication methods (no auth }
// for now) return super.getPort();
out.write(0); // the authentication (none) }
if (auth) {
out.write(2);
}
out.flush();
if (in.read() != 0x05) // remote proxy version
throw new IOException("Proxy server is not supported!");
switch (in.read()) { // auth method
case 0:
break; // no auth
case 2:
// username and pass stuff
out.write(0x01); // user/pass version #
out.write(username.length());
out.write(username.getBytes());
out.write(password.length());
out.write(password.getBytes());
out.flush();
in.read(); // skip the version
if (in.read() == 0) // Successful login, continue
break;
default:
throw new IOException("Proxy server declined request!");
}
// now to write the actual request @Override
out.write(0x05); // again the socks version public InetAddress getInetAddress() {
out.write(0x01); // the connection type (0x01 = TCP Connection) if (super.getInetAddress().equals(proxyInetAddress)) {
out.write(0x00); // the reserve byte, un-used return addr;
byte[] b = addr.getAddress(); }
out.write(b.length == 4 ? 0x01 : 0x04); // if ipv4 or ipv6 (0x03 = return super.getInetAddress();
// domain name, but that's }
// unsupported as of yet)
out.write(b);
out.writeShort(port);
out.flush();
// now to read the server's reply @Override
if (in.read() != 0x05) // socks version (again) public SocketAddress getRemoteSocketAddress() {
throw new IOException("Proxy server dun goofed"); if (super.getInetAddress().equals(proxyInetAddress)) {
int reply = in.read(); return cachedAddr;
if (reply == 0x08) }
throw new IOException("Bad address sent to proxy server"); return super.getRemoteSocketAddress();
if (reply != 0x00) }
throw new IOException("Unable to connect to server!");
in.read(); // reserve byte
int addrType = in.read();
b = new byte[4];
switch (addrType) {
case 0x01:
b = new byte[4];
break;
case 0x04:
b = new byte[16];
break;
default:
throw new IOException("Bad address type from proxy server!");
}
in.readFully(b);
in.readShort(); // the returned port #, ignored
}
@Override @Override
public int getPort() { public SocketChannel getChannel() {
if (super.getInetAddress().equals(proxyInetAddress)) if (super.getInetAddress().equals(proxyInetAddress)) {
return port; return null;
return super.getPort(); }
} return super.getChannel();
}
@Override @Override
public InetAddress getInetAddress() { public void close() throws IOException {
if (super.getInetAddress().equals(proxyInetAddress)) connections.remove(this);
return addr; super.close();
return super.getInetAddress(); }
}
@Override
public SocketAddress getRemoteSocketAddress() {
if (super.getInetAddress().equals(proxyInetAddress))
return cachedAddr;
return super.getRemoteSocketAddress();
}
@Override
public SocketChannel getChannel() {
if (super.getInetAddress().equals(proxyInetAddress))
return null;
return super.getChannel();
}
@Override
public void close() throws IOException {
connections.remove(this);
super.close();
}
public static void setType(ProxyType pt) {
proxyType = pt;
}
public static int getConnectionCount() {
return connections.size();
}
public static void setLogin(String user, char[] pass) {
setLogin(user, new String(pass));
}
public static void setLogin(String user, String pass) {
username = user;
password = pass;
}
} }
@@ -1,5 +1,5 @@
package org.parabot.core.network.proxy; package org.parabot.core.network.proxy;
public enum ProxyType { public enum ProxyType {
NONE,SOCKS5, SOCKS4, HTTP NONE, SOCKS5, SOCKS4, HTTP
} }
@@ -3,23 +3,20 @@ package org.parabot.core.paint;
import org.parabot.environment.api.interfaces.Paintable; import org.parabot.environment.api.interfaces.Paintable;
/** /**
*
* Abstract class for debugging in game values & more * Abstract class for debugging in game values & more
* *
* @author Everel * @author Everel
*
*/ */
public abstract class AbstractDebugger implements Paintable { public abstract class AbstractDebugger implements Paintable {
/** /**
* Toggles this debugger * Toggles this debugger
*/
public abstract void toggle();
/**
*
* @return True if this debugger is enabled, otherwise false
*/ */
public abstract boolean isEnabled(); public abstract void toggle();
/**
* @return True if this debugger is enabled, otherwise false
*/
public abstract boolean isEnabled();
} }
@@ -1,61 +1,58 @@
package org.parabot.core.paint; package org.parabot.core.paint;
import java.awt.Color; import org.parabot.core.Context;
import java.awt.Graphics;
import java.awt.*;
import java.util.HashMap; import java.util.HashMap;
import java.util.LinkedList; import java.util.LinkedList;
import java.util.Queue; import java.util.Queue;
import org.parabot.core.Context;
/** /**
*
* Manages and paints on a collection of AbstractDebuggers * Manages and paints on a collection of AbstractDebuggers
* *
* @author Everel * @author Everel
*
*/ */
public class PaintDebugger { public class PaintDebugger {
private final HashMap<String, AbstractDebugger> debuggers; private final HashMap<String, AbstractDebugger> debuggers;
private final Queue<String> stringDebug; private final Queue<String> stringDebug;
public PaintDebugger() { public PaintDebugger() {
this.debuggers = new HashMap<String, AbstractDebugger>(); this.debuggers = new HashMap<String, AbstractDebugger>();
this.stringDebug = new LinkedList<String>(); this.stringDebug = new LinkedList<String>();
} }
public final void addDebugger(final String name, final AbstractDebugger debugger) { public static final PaintDebugger getInstance() {
debuggers.put(name, debugger); return Context.getInstance().getPaintDebugger();
} }
public void debug(Graphics g) { public final void addDebugger(final String name, final AbstractDebugger debugger) {
for(final AbstractDebugger d : debuggers.values()) { debuggers.put(name, debugger);
if(d.isEnabled()) { }
d.paint(g);
}
}
g.setColor(Color.green);
int y = 40;
while(stringDebug.size() > 0) {
g.drawString(stringDebug.poll(), 10, y);
y += 15;
}
}
public static final PaintDebugger getInstance() { public void debug(Graphics g) {
return Context.getInstance().getPaintDebugger(); for (final AbstractDebugger d : debuggers.values()) {
} if (d.isEnabled()) {
d.paint(g);
}
}
g.setColor(Color.green);
int y = 40;
while (stringDebug.size() > 0) {
g.drawString(stringDebug.poll(), 10, y);
y += 15;
}
}
public final void addLine(final String debugLine) { public final void addLine(final String debugLine) {
stringDebug.add(debugLine); stringDebug.add(debugLine);
} }
public final void toggle(final String name) { public final void toggle(final String name) {
debuggers.get(name).toggle(); debuggers.get(name).toggle();
} }
public final boolean isEnabled(final String name) { public final boolean isEnabled(final String name) {
return debuggers.get(name).isEnabled(); return debuggers.get(name).isEnabled();
} }
} }
@@ -3,6 +3,7 @@ package org.parabot.core.parsers.hooks;
import org.parabot.core.asm.hooks.HookFile; import org.parabot.core.asm.hooks.HookFile;
import org.parabot.core.asm.interfaces.Injectable; import org.parabot.core.asm.interfaces.Injectable;
import org.parabot.core.asm.wrappers.*; import org.parabot.core.asm.wrappers.*;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Collections; import java.util.Collections;
import java.util.HashMap; import java.util.HashMap;
@@ -15,7 +16,6 @@ import java.util.HashMap;
*/ */
public abstract class HookParser { public abstract class HookParser {
public HookParser(HookFile hookFile) { public HookParser(HookFile hookFile) {
} }
@@ -36,7 +36,7 @@ public abstract class HookParser {
public Injectable[] getInjectables() { public Injectable[] getInjectables() {
ArrayList<Injectable> injectables = new ArrayList<Injectable>(); ArrayList<Injectable> injectables = new ArrayList<Injectable>();
Interface[] interfaces = getInterfaces(); Interface[] interfaces = getInterfaces();
if (interfaces != null) { if (interfaces != null) {
Collections.addAll(injectables, interfaces); Collections.addAll(injectables, interfaces);
} }
@@ -1,248 +1,241 @@
package org.parabot.core.parsers.hooks; package org.parabot.core.parsers.hooks;
import java.io.InputStreamReader;
import java.util.HashMap;
import java.util.Map;
import org.json.simple.JSONArray; import org.json.simple.JSONArray;
import org.json.simple.JSONObject; import org.json.simple.JSONObject;
import org.json.simple.parser.JSONParser; import org.json.simple.parser.JSONParser;
import org.parabot.core.asm.adapters.AddInterfaceAdapter; import org.parabot.core.asm.adapters.AddInterfaceAdapter;
import org.parabot.core.asm.hooks.HookFile; import org.parabot.core.asm.hooks.HookFile;
import org.parabot.core.asm.wrappers.Callback; import org.parabot.core.asm.wrappers.*;
import org.parabot.core.asm.wrappers.Getter;
import org.parabot.core.asm.wrappers.Interface; import java.io.InputStreamReader;
import org.parabot.core.asm.wrappers.Invoker; import java.util.HashMap;
import org.parabot.core.asm.wrappers.Setter; import java.util.Map;
import org.parabot.core.asm.wrappers.Super;
/** /**
*
* @author Dane * @author Dane
*
*/ */
public class JSONHookParser extends HookParser { public class JSONHookParser extends HookParser {
private JSONObject root; private JSONObject root;
private Map<String, String> interfaces; private Map<String, String> interfaces;
private HashMap<String, String> constants; private HashMap<String, String> constants;
public JSONHookParser(HookFile file) { public JSONHookParser(HookFile file) {
super(file); super(file);
JSONParser parser = new JSONParser(); JSONParser parser = new JSONParser();
try { try {
parser.parse(new InputStreamReader(file.getInputStream())); parser.parse(new InputStreamReader(file.getInputStream()));
} catch (Throwable t) { } catch (Throwable t) {
throw new RuntimeException("Unable to parse hooks: " + t); throw new RuntimeException("Unable to parse hooks: " + t);
} }
} }
public String get(JSONObject o, String s) { public String get(JSONObject o, String s) {
return this.get(o, s); return this.get(o, s);
} }
public String formatDescription(String s) { public String formatDescription(String s) {
StringBuilder b = new StringBuilder(); StringBuilder b = new StringBuilder();
if (s.charAt(0) == '[') { if (s.charAt(0) == '[') {
for (int j = 0; j < s.length(); j++) { for (int j = 0; j < s.length(); j++) {
if (s.charAt(j) == '[') { if (s.charAt(j) == '[') {
b.append('['); b.append('[');
} }
} }
s = s.replaceAll("\\[", ""); s = s.replaceAll("\\[", "");
} }
return b.append('L').append(String.format(s, AddInterfaceAdapter.getAccessorPackage())).append(';').toString(); return b.append('L').append(String.format(s, AddInterfaceAdapter.getAccessorPackage())).append(';').toString();
} }
@Override @Override
public Interface[] getInterfaces() { public Interface[] getInterfaces() {
JSONArray a = (JSONArray) root.get("interfaces"); JSONArray a = (JSONArray) root.get("interfaces");
interfaces = new HashMap<>(); interfaces = new HashMap<>();
if (a != null && a.size() > 0) { if (a != null && a.size() > 0) {
Interface[] i = new Interface[a.size()]; Interface[] i = new Interface[a.size()];
for (int j = 0; j < a.size(); j++) { for (int j = 0; j < a.size(); j++) {
JSONObject o = (JSONObject) a.get(j); JSONObject o = (JSONObject) a.get(j);
String clazz = this.get(o, "class"); String clazz = this.get(o, "class");
String interfaze = this.get(o, "interface"); String interfaze = this.get(o, "interface");
interfaces.put(clazz, interfaze); interfaces.put(clazz, interfaze);
i[j] = new Interface(clazz, interfaze); i[j] = new Interface(clazz, interfaze);
} }
return i; return i;
} }
return null; return null;
} }
@Override @Override
public Super[] getSupers() { public Super[] getSupers() {
JSONArray a = (JSONArray) root.get("supers"); JSONArray a = (JSONArray) root.get("supers");
if (a != null && a.size() > 0) { if (a != null && a.size() > 0) {
Super[] s = new Super[a.size()]; Super[] s = new Super[a.size()];
for (int i = 0; i < a.size(); i++) { for (int i = 0; i < a.size(); i++) {
JSONObject o = (JSONObject) a.get(i); JSONObject o = (JSONObject) a.get(i);
s[i] = new Super(this.get(o, "class"), this.get(o, "super")); s[i] = new Super(this.get(o, "class"), this.get(o, "super"));
} }
return s; return s;
} }
return null; return null;
} }
@Override @Override
public Getter[] getGetters() { public Getter[] getGetters() {
JSONArray a = (JSONArray) root.get("getters"); JSONArray a = (JSONArray) root.get("getters");
if (a != null && a.size() > 0) { if (a != null && a.size() > 0) {
Getter[] g = new Getter[a.size()]; Getter[] g = new Getter[a.size()];
for (int i = 0; i < a.size(); i++) { for (int i = 0; i < a.size(); i++) {
JSONObject o = (JSONObject) a.get(i); JSONObject o = (JSONObject) a.get(i);
if (o.containsKey("class") && o.containsKey("accessor")) { if (o.containsKey("class") && o.containsKey("accessor")) {
throw new RuntimeException("Cannot have class AND accessor tags together!"); throw new RuntimeException("Cannot have class AND accessor tags together!");
} }
if (o.containsKey("accessor") && this.interfaces == null) { if (o.containsKey("accessor") && this.interfaces == null) {
throw new RuntimeException("Cannot use accessor tag before parsing interfaces!"); throw new RuntimeException("Cannot use accessor tag before parsing interfaces!");
} }
String desc = this.get(o, "desc"); String desc = this.get(o, "desc");
if (desc != null && desc.contains("%s")) { if (desc != null && desc.contains("%s")) {
desc = formatDescription(desc); desc = formatDescription(desc);
} }
String clazz = o.containsKey("class") ? this.get(o, "class") : interfaces.get(this.get(o, "accessor")); String clazz = o.containsKey("class") ? this.get(o, "class") : interfaces.get(this.get(o, "accessor"));
String into = o.containsKey("into") ? this.get(o, "into") : clazz; String into = o.containsKey("into") ? this.get(o, "into") : clazz;
g[i] = new Getter(into, clazz, this.get(o, "field"), this.get(o, "method"), desc, o.containsKey("static") ? (boolean) o.get("static") : false, 0, null); g[i] = new Getter(into, clazz, this.get(o, "field"), this.get(o, "method"), desc, o.containsKey("static") ? (boolean) o.get("static") : false, 0, null);
} }
return g; return g;
} }
return null; return null;
} }
@Override @Override
public Setter[] getSetters() { public Setter[] getSetters() {
JSONArray a = (JSONArray) root.get("setters"); JSONArray a = (JSONArray) root.get("setters");
if (a != null && a.size() > 0) { if (a != null && a.size() > 0) {
Setter[] s = new Setter[a.size()]; Setter[] s = new Setter[a.size()];
for (int i = 0; i < a.size(); i++) { for (int i = 0; i < a.size(); i++) {
JSONObject o = (JSONObject) a.get(i); JSONObject o = (JSONObject) a.get(i);
if (o.containsKey("class") && o.containsKey("accessor")) { if (o.containsKey("class") && o.containsKey("accessor")) {
throw new RuntimeException("Cannot have class AND accessor tags together!"); throw new RuntimeException("Cannot have class AND accessor tags together!");
} }
if (o.containsKey("accessor") && this.interfaces == null) { if (o.containsKey("accessor") && this.interfaces == null) {
throw new RuntimeException("Cannot use accessor tag before parsing interfaces!"); throw new RuntimeException("Cannot use accessor tag before parsing interfaces!");
} }
String desc = this.get(o, "desc"); String desc = this.get(o, "desc");
if (desc != null && desc.contains("%s")) { if (desc != null && desc.contains("%s")) {
desc = formatDescription(desc); desc = formatDescription(desc);
} }
String clazz = o.containsKey("class") ? this.get(o, "class") : interfaces.get(this.get(o, "accessor")); String clazz = o.containsKey("class") ? this.get(o, "class") : interfaces.get(this.get(o, "accessor"));
String into = o.containsKey("into") ? this.get(o, "into") : clazz; String into = o.containsKey("into") ? this.get(o, "into") : clazz;
s[i] = new Setter(into, clazz, this.get(o, "field"), this.get(o, "method"), desc, o.containsKey("static") ? (boolean) o.get("static") : false, null); s[i] = new Setter(into, clazz, this.get(o, "field"), this.get(o, "method"), desc, o.containsKey("static") ? (boolean) o.get("static") : false, null);
} }
return s; return s;
} }
return null; return null;
} }
@Override @Override
public Invoker[] getInvokers() { public Invoker[] getInvokers() {
JSONArray a = (JSONArray) root.get("invokers"); JSONArray a = (JSONArray) root.get("invokers");
if (a != null && a.size() > 0) { if (a != null && a.size() > 0) {
Invoker[] i = new Invoker[a.size()]; Invoker[] i = new Invoker[a.size()];
for (int j = 0; j < a.size(); j++) { for (int j = 0; j < a.size(); j++) {
JSONObject o = (JSONObject) a.get(j); JSONObject o = (JSONObject) a.get(j);
if (o.containsKey("class") && o.containsKey("accessor")) { if (o.containsKey("class") && o.containsKey("accessor")) {
throw new RuntimeException("Cannot have class AND accessor tags together!"); throw new RuntimeException("Cannot have class AND accessor tags together!");
} }
if (o.containsKey("accessor") && this.interfaces == null) { if (o.containsKey("accessor") && this.interfaces == null) {
throw new RuntimeException("Cannot use accessor tag before parsing interfaces!"); throw new RuntimeException("Cannot use accessor tag before parsing interfaces!");
} }
String desc = this.get(o, "desc"); String desc = this.get(o, "desc");
if (desc != null && desc.contains("%s")) { if (desc != null && desc.contains("%s")) {
desc = formatDescription(desc); desc = formatDescription(desc);
} }
String clazz = o.containsKey("class") ? this.get(o, "class") : interfaces.get(this.get(o, "accessor")); String clazz = o.containsKey("class") ? this.get(o, "class") : interfaces.get(this.get(o, "accessor"));
String into = o.containsKey("into") ? this.get(o, "into") : clazz; String into = o.containsKey("into") ? this.get(o, "into") : clazz;
i[j] = new Invoker(into, clazz, this.get(o, "invokemethod"), this.get(o, "argdesc"), this.get(o, "desc"), this.get(o, "method"), false, null, null); i[j] = new Invoker(into, clazz, this.get(o, "invokemethod"), this.get(o, "argdesc"), this.get(o, "desc"), this.get(o, "method"), false, null, null);
} }
return i; return i;
} }
return null; return null;
} }
@Override @Override
public Callback[] getCallbacks() { public Callback[] getCallbacks() {
JSONArray a = (JSONArray) root.get("callbacks"); JSONArray a = (JSONArray) root.get("callbacks");
if (a != null && a.size() > 0) { if (a != null && a.size() > 0) {
Callback[] c = new Callback[a.size()]; Callback[] c = new Callback[a.size()];
for (int j = 0; j < a.size(); j++) { for (int j = 0; j < a.size(); j++) {
JSONObject o = (JSONObject) a.get(j); JSONObject o = (JSONObject) a.get(j);
if (o.containsKey("class") && o.containsKey("accessor")) { if (o.containsKey("class") && o.containsKey("accessor")) {
throw new RuntimeException("Cannot have class AND accessor tags together!"); throw new RuntimeException("Cannot have class AND accessor tags together!");
} }
if (o.containsKey("accessor") && this.interfaces == null) { if (o.containsKey("accessor") && this.interfaces == null) {
throw new RuntimeException("Cannot use accessor tag before parsing interfaces!"); throw new RuntimeException("Cannot use accessor tag before parsing interfaces!");
} }
String desc = this.get(o, "desc"); String desc = this.get(o, "desc");
if (desc != null && desc.contains("%s")) { if (desc != null && desc.contains("%s")) {
desc = formatDescription(desc); desc = formatDescription(desc);
} }
String clazz = o.containsKey("class") ? this.get(o, "class") : interfaces.get(this.get(o, "accessor")); String clazz = o.containsKey("class") ? this.get(o, "class") : interfaces.get(this.get(o, "accessor"));
c[j] = new Callback(clazz, this.get(o, "method"), this.get(o, "callclass"), this.get(o, "callmethod"), this.get(o, "calldesc"), this.get(o, "callargs"), this.get(o, "desc"), false); c[j] = new Callback(clazz, this.get(o, "method"), this.get(o, "callclass"), this.get(o, "callmethod"), this.get(o, "calldesc"), this.get(o, "callargs"), this.get(o, "desc"), false);
} }
return c; return c;
} }
return null; return null;
} }
@Override @Override
public HashMap<String, String> getConstants() { public HashMap<String, String> getConstants() {
if (this.constants == null) { if (this.constants == null) {
this.constants = new HashMap<>(); this.constants = new HashMap<>();
} }
if (!this.constants.isEmpty()) { if (!this.constants.isEmpty()) {
return this.constants; return this.constants;
} }
JSONArray a = (JSONArray) root.get("constants"); JSONArray a = (JSONArray) root.get("constants");
if (a != null && a.size() > 0) { if (a != null && a.size() > 0) {
for (int j = 0; j < a.size(); j++) { for (int j = 0; j < a.size(); j++) {
JSONObject o = (JSONObject) a.get(j); JSONObject o = (JSONObject) a.get(j);
this.constants.put(this.get(o, "name"), (String) o.get("value")); this.constants.put(this.get(o, "name"), (String) o.get("value"));
} }
} }
return this.constants; return this.constants;
} }
} }
@@ -1,274 +1,44 @@
package org.parabot.core.parsers.hooks; package org.parabot.core.parsers.hooks;
import java.util.ArrayList;
import java.util.HashMap;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import org.parabot.core.Core; import org.parabot.core.Core;
import org.parabot.core.asm.adapters.AddInterfaceAdapter; import org.parabot.core.asm.adapters.AddInterfaceAdapter;
import org.parabot.core.asm.hooks.HookFile; import org.parabot.core.asm.hooks.HookFile;
import org.parabot.core.asm.wrappers.Callback; import org.parabot.core.asm.wrappers.*;
import org.parabot.core.asm.wrappers.Getter;
import org.parabot.core.asm.wrappers.Interface;
import org.parabot.core.asm.wrappers.Invoker;
import org.parabot.core.asm.wrappers.Setter;
import org.parabot.core.asm.wrappers.Super;
import org.w3c.dom.Document; import org.w3c.dom.Document;
import org.w3c.dom.Element; import org.w3c.dom.Element;
import org.w3c.dom.Node; import org.w3c.dom.Node;
import org.w3c.dom.NodeList; import org.w3c.dom.NodeList;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import java.util.ArrayList;
import java.util.HashMap;
public class XMLHookParser extends HookParser { public class XMLHookParser extends HookParser {
private Document doc; private Document doc;
private HashMap<String, String> interfaceMap; private HashMap<String, String> interfaceMap;
private HashMap<String, String> constants; private HashMap<String, String> constants;
private boolean parsedInterfaces; private boolean parsedInterfaces;
public XMLHookParser(HookFile hookFile) { public XMLHookParser(HookFile hookFile) {
super(hookFile); super(hookFile);
interfaceMap = new HashMap<String, String>(); interfaceMap = new HashMap<String, String>();
constants = new HashMap<String, String>(); constants = new HashMap<String, String>();
try { try {
DocumentBuilderFactory dbFactory = DocumentBuilderFactory DocumentBuilderFactory dbFactory = DocumentBuilderFactory
.newInstance(); .newInstance();
DocumentBuilder dBuilder = dbFactory.newDocumentBuilder(); DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
doc = dBuilder.parse(hookFile.getInputStream()); doc = dBuilder.parse(hookFile.getInputStream());
doc.getDocumentElement().normalize(); doc.getDocumentElement().normalize();
if (!doc.getDocumentElement().getNodeName().equals("injector")) { if (!doc.getDocumentElement().getNodeName().equals("injector")) {
throw new RuntimeException("Incorrect hook file."); throw new RuntimeException("Incorrect hook file.");
}
} catch (Throwable t) {
throw new RuntimeException("Unable to parse hooks " + t);
}
}
@Override
public Interface[] getInterfaces() {
parsedInterfaces = true;
final NodeList interfaceRootList = doc
.getElementsByTagName("interfaces");
switch (interfaceRootList.getLength()) {
case 0:
return null;
case 1:
break;
default:
throw new RuntimeException(
"Hook file may not contains multiple <interfaces> tags ");
}
final Node node = interfaceRootList.item(0);
if (node.getNodeType() != Node.ELEMENT_NODE) {
return null;
}
final Element interfaceRoot = (Element) node;
final NodeList interfaces = interfaceRoot.getElementsByTagName("add");
if (interfaces.getLength() == 0) {
return null;
}
final ArrayList<Interface> interfaceList = new ArrayList<Interface>();
for (int x = 0; x < interfaces.getLength(); x++) {
final Node n = interfaces.item(x);
if (n.getNodeType() != Node.ELEMENT_NODE) {
continue;
}
final Element addInterface = (Element) n;
final String className = getValue("classname", addInterface);
final String interfaceClass = getValue("interface", addInterface);
interfaceMap.put(interfaceClass, className);
final Interface inf = new Interface(className, interfaceClass);
interfaceList.add(inf);
}
return interfaceList.toArray(new Interface[interfaceList.size()]);
}
@Override
public Super[] getSupers() {
final NodeList interfaceRootList = doc.getElementsByTagName("supers");
switch (interfaceRootList.getLength()) {
case 0:
return null;
case 1:
break;
default:
throw new RuntimeException(
"Hook file may not contains multiple <supers> tags ");
}
final Node node = interfaceRootList.item(0);
if (node.getNodeType() != Node.ELEMENT_NODE) {
return null;
}
final Element superRoot = (Element) node;
final NodeList supers = superRoot.getElementsByTagName("add");
if (supers.getLength() == 0) {
return null;
}
final ArrayList<Super> superList = new ArrayList<Super>();
for (int x = 0; x < supers.getLength(); x++) {
final Node n = supers.item(x);
if (n.getNodeType() != Node.ELEMENT_NODE) {
continue;
} }
final Element addSuper = (Element) n; } catch (Throwable t) {
final String className = getValue("classname", addSuper); throw new RuntimeException("Unable to parse hooks " + t);
final String superClass = getValue("super", addSuper);
final Super sup = new Super(className, superClass);
superList.add(sup);
} }
return superList.toArray(new Super[superList.size()]); }
}
@Override private static String resolveDesc(String returnDesc) {
public Getter[] getGetters() {
final NodeList getterRootList = doc.getElementsByTagName("getters");
switch (getterRootList.getLength()) {
case 0:
return null;
case 1:
break;
default:
throw new RuntimeException(
"Hook file may not contains multiple <getters> tags ");
}
final Node node = getterRootList.item(0);
if (node.getNodeType() != Node.ELEMENT_NODE) {
return null;
}
final Element getterRoot = (Element) node;
final NodeList getters = getterRoot.getElementsByTagName("add");
if (getters.getLength() == 0) {
return null;
}
final ArrayList<Getter> getterList = new ArrayList<Getter>();
for (int x = 0; x < getters.getLength(); x++) {
final Node n = getters.item(x);
if (n.getNodeType() != Node.ELEMENT_NODE) {
continue;
}
final Element addGetter = (Element) n;
if (isSet("classname", addGetter) && isSet("accessor", addGetter)) {
throw new RuntimeException(
"Can't set classname and accessor tag together.");
}
if (isSet("accessor", addGetter) && !parsedInterfaces) {
throw new RuntimeException(
"You'll need to parse interfaces first.");
}
final String className = isSet("classname", addGetter) ? getValue(
"classname", addGetter) : interfaceMap.get(getValue(
"accessor", addGetter));
final String into = isSet("into", addGetter) ? getValue("into",
addGetter) : className;
final long multiplier = isSet("multiplier", addGetter) ? Long.parseLong(getValue("multiplier", addGetter)) : 0L;
final String fieldName = getValue("field", addGetter);
final String fieldDesc = isSet("descfield", addGetter) ? getValue("descfield", addGetter) : null;
final String methodName = getValue("methodname", addGetter);
boolean staticMethod = isSet("methstatic", addGetter) ? (getValue(
"methstatic", addGetter).equals("true")) : false;
String returnDesc = isSet("desc", addGetter) ? getValue("desc",
addGetter) : null;
String array = "";
if (returnDesc != null && returnDesc.contains("%s")) {
StringBuilder str = new StringBuilder();
if (returnDesc.startsWith("[")) {
for (int i = 0; i < returnDesc.length(); i++) {
if (returnDesc.charAt(i) == '[') {
array += '[';
}
}
returnDesc = returnDesc.replaceAll("\\[", "");
}
str.append(array)
.append('L')
.append(String.format(returnDesc,
AddInterfaceAdapter.getAccessorPackage()))
.append(";");
returnDesc = str.toString();
}
final Getter get = new Getter(into, className, fieldName,
methodName, returnDesc, staticMethod, multiplier, fieldDesc);
getterList.add(get);
}
Core.verbose("Fields hooked: " + getterList.size());
return getterList.toArray(new Getter[getterList.size()]);
}
@Override
public Setter[] getSetters() {
final NodeList setterRootList = doc.getElementsByTagName("setters");
switch (setterRootList.getLength()) {
case 0:
return null;
case 1:
break;
default:
throw new RuntimeException(
"Hook file may not contains multiple <setters> tags ");
}
final Node node = setterRootList.item(0);
if (node.getNodeType() != Node.ELEMENT_NODE) {
return null;
}
final Element setterRoot = (Element) node;
final NodeList setters = setterRoot.getElementsByTagName("add");
if (setters.getLength() == 0) {
return null;
}
final ArrayList<Setter> setterList = new ArrayList<Setter>();
for (int x = 0; x < setters.getLength(); x++) {
final Node n = setters.item(x);
if (n.getNodeType() != Node.ELEMENT_NODE) {
continue;
}
final Element addSetter = (Element) n;
if (isSet("classname", addSetter) && isSet("accessor", addSetter)) {
throw new RuntimeException(
"Can't set classname and accessor tag together.");
}
if (isSet("accessor", addSetter) && !parsedInterfaces) {
throw new RuntimeException(
"You'll need to parse interfaces first.");
}
final String className = isSet("classname", addSetter) ? getValue(
"classname", addSetter) : interfaceMap.get(getValue(
"accessor", addSetter));
final String into = isSet("into", addSetter) ? getValue("into",
addSetter) : className;
final String fieldName = getValue("field", addSetter);
final String fieldDesc = isSet("descfield", addSetter) ? getValue("descfield", addSetter) : null;
final String methodName = getValue("methodname", addSetter);
boolean staticMethod = isSet("methstatic", addSetter) ? (getValue(
"methstatic", addSetter).equals("true")) : false;
String returnDesc = isSet("desc", addSetter) ? getValue("desc",
addSetter) : null;
String array = "";
if (returnDesc != null && returnDesc.contains("%s")) {
StringBuilder str = new StringBuilder();
if (returnDesc.startsWith("[")) {
for (int i = 0; i < returnDesc.length(); i++) {
if (returnDesc.charAt(i) == '[') {
array += '[';
}
}
returnDesc = returnDesc.replaceAll("\\[", "");
}
str.append(array)
.append('L')
.append(String.format(returnDesc,
AddInterfaceAdapter.getAccessorPackage()))
.append(";");
returnDesc = str.toString();
}
final Setter get = new Setter(className, into, fieldName,
methodName, returnDesc, staticMethod, fieldDesc);
setterList.add(get);
}
return setterList.toArray(new Setter[setterList.size()]);
}
private static String resolveDesc(String returnDesc) {
String array = ""; String array = "";
if (returnDesc != null && returnDesc.contains("%s")) { if (returnDesc != null && returnDesc.contains("%s")) {
StringBuilder str = new StringBuilder(); StringBuilder str = new StringBuilder();
@@ -301,9 +71,232 @@ public class XMLHookParser extends HookParser {
return node.getNodeValue(); return node.getNodeValue();
} }
@Override @Override
public Invoker[] getInvokers() { public Interface[] getInterfaces() {
final NodeList invokerRootList = doc.getElementsByTagName("invokers"); parsedInterfaces = true;
final NodeList interfaceRootList = doc
.getElementsByTagName("interfaces");
switch (interfaceRootList.getLength()) {
case 0:
return null;
case 1:
break;
default:
throw new RuntimeException(
"Hook file may not contains multiple <interfaces> tags ");
}
final Node node = interfaceRootList.item(0);
if (node.getNodeType() != Node.ELEMENT_NODE) {
return null;
}
final Element interfaceRoot = (Element) node;
final NodeList interfaces = interfaceRoot.getElementsByTagName("add");
if (interfaces.getLength() == 0) {
return null;
}
final ArrayList<Interface> interfaceList = new ArrayList<Interface>();
for (int x = 0; x < interfaces.getLength(); x++) {
final Node n = interfaces.item(x);
if (n.getNodeType() != Node.ELEMENT_NODE) {
continue;
}
final Element addInterface = (Element) n;
final String className = getValue("classname", addInterface);
final String interfaceClass = getValue("interface", addInterface);
interfaceMap.put(interfaceClass, className);
final Interface inf = new Interface(className, interfaceClass);
interfaceList.add(inf);
}
return interfaceList.toArray(new Interface[interfaceList.size()]);
}
@Override
public Super[] getSupers() {
final NodeList interfaceRootList = doc.getElementsByTagName("supers");
switch (interfaceRootList.getLength()) {
case 0:
return null;
case 1:
break;
default:
throw new RuntimeException(
"Hook file may not contains multiple <supers> tags ");
}
final Node node = interfaceRootList.item(0);
if (node.getNodeType() != Node.ELEMENT_NODE) {
return null;
}
final Element superRoot = (Element) node;
final NodeList supers = superRoot.getElementsByTagName("add");
if (supers.getLength() == 0) {
return null;
}
final ArrayList<Super> superList = new ArrayList<Super>();
for (int x = 0; x < supers.getLength(); x++) {
final Node n = supers.item(x);
if (n.getNodeType() != Node.ELEMENT_NODE) {
continue;
}
final Element addSuper = (Element) n;
final String className = getValue("classname", addSuper);
final String superClass = getValue("super", addSuper);
final Super sup = new Super(className, superClass);
superList.add(sup);
}
return superList.toArray(new Super[superList.size()]);
}
@Override
public Getter[] getGetters() {
final NodeList getterRootList = doc.getElementsByTagName("getters");
switch (getterRootList.getLength()) {
case 0:
return null;
case 1:
break;
default:
throw new RuntimeException(
"Hook file may not contains multiple <getters> tags ");
}
final Node node = getterRootList.item(0);
if (node.getNodeType() != Node.ELEMENT_NODE) {
return null;
}
final Element getterRoot = (Element) node;
final NodeList getters = getterRoot.getElementsByTagName("add");
if (getters.getLength() == 0) {
return null;
}
final ArrayList<Getter> getterList = new ArrayList<Getter>();
for (int x = 0; x < getters.getLength(); x++) {
final Node n = getters.item(x);
if (n.getNodeType() != Node.ELEMENT_NODE) {
continue;
}
final Element addGetter = (Element) n;
if (isSet("classname", addGetter) && isSet("accessor", addGetter)) {
throw new RuntimeException(
"Can't set classname and accessor tag together.");
}
if (isSet("accessor", addGetter) && !parsedInterfaces) {
throw new RuntimeException(
"You'll need to parse interfaces first.");
}
final String className = isSet("classname", addGetter) ? getValue(
"classname", addGetter) : interfaceMap.get(getValue(
"accessor", addGetter));
final String into = isSet("into", addGetter) ? getValue("into",
addGetter) : className;
final long multiplier = isSet("multiplier", addGetter) ? Long.parseLong(getValue("multiplier", addGetter)) : 0L;
final String fieldName = getValue("field", addGetter);
final String fieldDesc = isSet("descfield", addGetter) ? getValue("descfield", addGetter) : null;
final String methodName = getValue("methodname", addGetter);
boolean staticMethod = isSet("methstatic", addGetter) ? (getValue(
"methstatic", addGetter).equals("true")) : false;
String returnDesc = isSet("desc", addGetter) ? getValue("desc",
addGetter) : null;
String array = "";
if (returnDesc != null && returnDesc.contains("%s")) {
StringBuilder str = new StringBuilder();
if (returnDesc.startsWith("[")) {
for (int i = 0; i < returnDesc.length(); i++) {
if (returnDesc.charAt(i) == '[') {
array += '[';
}
}
returnDesc = returnDesc.replaceAll("\\[", "");
}
str.append(array)
.append('L')
.append(String.format(returnDesc,
AddInterfaceAdapter.getAccessorPackage()))
.append(";");
returnDesc = str.toString();
}
final Getter get = new Getter(into, className, fieldName,
methodName, returnDesc, staticMethod, multiplier, fieldDesc);
getterList.add(get);
}
Core.verbose("Fields hooked: " + getterList.size());
return getterList.toArray(new Getter[getterList.size()]);
}
@Override
public Setter[] getSetters() {
final NodeList setterRootList = doc.getElementsByTagName("setters");
switch (setterRootList.getLength()) {
case 0:
return null;
case 1:
break;
default:
throw new RuntimeException(
"Hook file may not contains multiple <setters> tags ");
}
final Node node = setterRootList.item(0);
if (node.getNodeType() != Node.ELEMENT_NODE) {
return null;
}
final Element setterRoot = (Element) node;
final NodeList setters = setterRoot.getElementsByTagName("add");
if (setters.getLength() == 0) {
return null;
}
final ArrayList<Setter> setterList = new ArrayList<Setter>();
for (int x = 0; x < setters.getLength(); x++) {
final Node n = setters.item(x);
if (n.getNodeType() != Node.ELEMENT_NODE) {
continue;
}
final Element addSetter = (Element) n;
if (isSet("classname", addSetter) && isSet("accessor", addSetter)) {
throw new RuntimeException(
"Can't set classname and accessor tag together.");
}
if (isSet("accessor", addSetter) && !parsedInterfaces) {
throw new RuntimeException(
"You'll need to parse interfaces first.");
}
final String className = isSet("classname", addSetter) ? getValue(
"classname", addSetter) : interfaceMap.get(getValue(
"accessor", addSetter));
final String into = isSet("into", addSetter) ? getValue("into",
addSetter) : className;
final String fieldName = getValue("field", addSetter);
final String fieldDesc = isSet("descfield", addSetter) ? getValue("descfield", addSetter) : null;
final String methodName = getValue("methodname", addSetter);
boolean staticMethod = isSet("methstatic", addSetter) ? (getValue(
"methstatic", addSetter).equals("true")) : false;
String returnDesc = isSet("desc", addSetter) ? getValue("desc",
addSetter) : null;
String array = "";
if (returnDesc != null && returnDesc.contains("%s")) {
StringBuilder str = new StringBuilder();
if (returnDesc.startsWith("[")) {
for (int i = 0; i < returnDesc.length(); i++) {
if (returnDesc.charAt(i) == '[') {
array += '[';
}
}
returnDesc = returnDesc.replaceAll("\\[", "");
}
str.append(array)
.append('L')
.append(String.format(returnDesc,
AddInterfaceAdapter.getAccessorPackage()))
.append(";");
returnDesc = str.toString();
}
final Setter get = new Setter(className, into, fieldName,
methodName, returnDesc, staticMethod, fieldDesc);
setterList.add(get);
}
return setterList.toArray(new Setter[setterList.size()]);
}
@Override
public Invoker[] getInvokers() {
final NodeList invokerRootList = doc.getElementsByTagName("invokers");
switch (invokerRootList.getLength()) { switch (invokerRootList.getLength()) {
case 0: case 0:
return null; return null;
@@ -317,8 +310,8 @@ public class XMLHookParser extends HookParser {
if (node.getNodeType() != Node.ELEMENT_NODE) { if (node.getNodeType() != Node.ELEMENT_NODE) {
return null; return null;
} }
final Element invokerRoot = (Element) node; final Element invokerRoot = (Element) node;
final NodeList invokers = invokerRoot.getElementsByTagName("add"); final NodeList invokers = invokerRoot.getElementsByTagName("add");
if (invokers.getLength() == 0) { if (invokers.getLength() == 0) {
return null; return null;
} }
@@ -342,26 +335,26 @@ public class XMLHookParser extends HookParser {
"accessor", addInvoker)); "accessor", addInvoker));
final String into = isSet("into", addInvoker) ? getValue("into", final String into = isSet("into", addInvoker) ? getValue("into",
addInvoker) : className; addInvoker) : className;
final String methodName = getValue("methodname", addInvoker); final String methodName = getValue("methodname", addInvoker);
final String invMethodName = getValue("invokemethod", addInvoker); final String invMethodName = getValue("invokemethod", addInvoker);
final String argsDesc = getValue("argsdesc", addInvoker); final String argsDesc = getValue("argsdesc", addInvoker);
String returnDesc = isSet("desc", addInvoker) ? resolveDesc(getValue( String returnDesc = isSet("desc", addInvoker) ? resolveDesc(getValue(
"desc", addInvoker)) : null; "desc", addInvoker)) : null;
final boolean isInterface = isSet("interface", addInvoker) ? Boolean.parseBoolean(getValue("interface", addInvoker)) : false; final boolean isInterface = isSet("interface", addInvoker) ? Boolean.parseBoolean(getValue("interface", addInvoker)) : false;
final String instanceCast = isSet("instancecast", addInvoker) ? getValue("instancecast", addInvoker) : null; final String instanceCast = isSet("instancecast", addInvoker) ? getValue("instancecast", addInvoker) : null;
final String checkCastArgsDesc = isSet("castargs", addInvoker) ? getValue("castargs", addInvoker) : null; final String checkCastArgsDesc = isSet("castargs", addInvoker) ? getValue("castargs", addInvoker) : null;
final Invoker invoker = new Invoker(into, className, invMethodName, final Invoker invoker = new Invoker(into, className, invMethodName,
argsDesc, returnDesc, methodName, isInterface, instanceCast, checkCastArgsDesc); argsDesc, returnDesc, methodName, isInterface, instanceCast, checkCastArgsDesc);
invokerList.add(invoker); invokerList.add(invoker);
} }
return invokerList.toArray(new Invoker[invokerList.size()]); return invokerList.toArray(new Invoker[invokerList.size()]);
} }
@Override @Override
public HashMap<String, String> getConstants() { public HashMap<String, String> getConstants() {
if (!constants.isEmpty()) { if (!constants.isEmpty()) {
return constants; return constants;
} }
final NodeList constantsRootList = doc final NodeList constantsRootList = doc
@@ -379,7 +372,7 @@ public class XMLHookParser extends HookParser {
if (node.getNodeType() != Node.ELEMENT_NODE) { if (node.getNodeType() != Node.ELEMENT_NODE) {
return null; return null;
} }
final Element constantRoot = (Element) node; final Element constantRoot = (Element) node;
final NodeList constantsList = constantRoot.getElementsByTagName("add"); final NodeList constantsList = constantRoot.getElementsByTagName("add");
if (constantsList.getLength() == 0) { if (constantsList.getLength() == 0) {
// return empty hashmap // return empty hashmap
@@ -391,16 +384,16 @@ public class XMLHookParser extends HookParser {
continue; continue;
} }
final Element addConstant = (Element) n; final Element addConstant = (Element) n;
final String key = getValue("key", addConstant); final String key = getValue("key", addConstant);
final String value = getValue("value", addConstant); final String value = getValue("value", addConstant);
constants.put(key, value); constants.put(key, value);
} }
return constants; return constants;
} }
@Override @Override
public Callback[] getCallbacks() { public Callback[] getCallbacks() {
final NodeList callbackRootList = doc.getElementsByTagName("callbacks"); final NodeList callbackRootList = doc.getElementsByTagName("callbacks");
switch (callbackRootList.getLength()) { switch (callbackRootList.getLength()) {
case 0: case 0:
return null; return null;
@@ -414,8 +407,8 @@ public class XMLHookParser extends HookParser {
if (node.getNodeType() != Node.ELEMENT_NODE) { if (node.getNodeType() != Node.ELEMENT_NODE) {
return null; return null;
} }
final Element callbackRoot = (Element) node; final Element callbackRoot = (Element) node;
final NodeList callbacks = callbackRoot.getElementsByTagName("add"); final NodeList callbacks = callbackRoot.getElementsByTagName("add");
if (callbacks.getLength() == 0) { if (callbacks.getLength() == 0) {
return null; return null;
} }
@@ -439,12 +432,12 @@ public class XMLHookParser extends HookParser {
"classname", addCallback) : interfaceMap.get(getValue( "classname", addCallback) : interfaceMap.get(getValue(
"accessor", addCallback)); "accessor", addCallback));
final String methodName = getValue("methodname", addCallback); final String methodName = getValue("methodname", addCallback);
final String callClass = getValue("callclass", addCallback); final String callClass = getValue("callclass", addCallback);
final String callMethod = getValue("callmethod", addCallback); final String callMethod = getValue("callmethod", addCallback);
final String callDesc = getValue("calldesc", addCallback); final String callDesc = getValue("calldesc", addCallback);
final String callArgs = getValue("callargs", addCallback); final String callArgs = getValue("callargs", addCallback);
final String desc = getValue("desc", addCallback); final String desc = getValue("desc", addCallback);
final boolean conditional = isSet("conditional", addCallback); final boolean conditional = isSet("conditional", addCallback);
final Callback callback = new Callback(className, methodName, desc, final Callback callback = new Callback(className, methodName, desc,
@@ -452,6 +445,6 @@ public class XMLHookParser extends HookParser {
callbackList.add(callback); callbackList.add(callback);
} }
return callbackList.toArray(new Callback[callbackList.size()]); return callbackList.toArray(new Callback[callbackList.size()]);
} }
} }
@@ -28,14 +28,14 @@ public class PublicRandoms extends RandomParser {
download(); download();
} }
try { try {
URL url = myJar.toURI().toURL(); URL url = myJar.toURI().toURL();
URL[] urls = new URL[]{url}; URL[] urls = new URL[]{ url };
String server = Context.getInstance().getServerProviderInfo().getServerName(); String server = Context.getInstance().getServerProviderInfo().getServerName();
URLClassLoader child = new URLClassLoader(urls, this.getClass().getClassLoader()); URLClassLoader child = new URLClassLoader(urls, this.getClass().getClassLoader());
Class<?> classToLoad = Class.forName("org.parabot.randoms.Core", true, child); Class<?> classToLoad = Class.forName("org.parabot.randoms.Core", true, child);
Method method = classToLoad.getDeclaredMethod("init", String.class); Method method = classToLoad.getDeclaredMethod("init", String.class);
Object instance = classToLoad.newInstance(); Object instance = classToLoad.newInstance();
System.out.println(server); System.out.println(server);
method.invoke(instance, server); method.invoke(instance, server);
Core.verbose("Successfully parsed public random!"); Core.verbose("Successfully parsed public random!");
@@ -40,19 +40,19 @@ public class BDNScripts extends ScriptParser {
JSONParser parser = new JSONParser(); JSONParser parser = new JSONParser();
try { try {
BufferedReader br = WebUtil.getReader(new URL( BufferedReader br = WebUtil.getReader(new URL(
Configuration.GET_SCRIPTS + Context.getInstance().getServerProviderInfo().getServerName()), Configuration.GET_SCRIPTS + Context.getInstance().getServerProviderInfo().getServerName()),
manager.getAccount().getURLUsername(), manager.getAccount().getURLPassword()); manager.getAccount().getURLUsername(), manager.getAccount().getURLPassword());
String line; String line;
while ((line = br.readLine()) != null) { while ((line = br.readLine()) != null) {
JSONObject jsonObject = (JSONObject) parser.parse(line); JSONObject jsonObject = (JSONObject) parser.parse(line);
int bdnId = Integer.parseInt(String.valueOf(jsonObject.get("id"))); int bdnId = Integer.parseInt(String.valueOf(jsonObject.get("id")));
String scriptName = String.valueOf(jsonObject.get("name")); String scriptName = String.valueOf(jsonObject.get("name"));
String author = String.valueOf(jsonObject.get("author")); String author = String.valueOf(jsonObject.get("author"));
double version = Double.parseDouble(String.valueOf(jsonObject.get("version"))); double version = Double.parseDouble(String.valueOf(jsonObject.get("version")));
String category = String.valueOf(jsonObject.get("category")); String category = String.valueOf(jsonObject.get("category"));
String description = String.valueOf(jsonObject.get("description")); String description = String.valueOf(jsonObject.get("description"));
final ScriptDescription desc = new ScriptDescription(scriptName, final ScriptDescription desc = new ScriptDescription(scriptName,
author, category, version, description, author, category, version, description,
@@ -1,14 +1,14 @@
package org.parabot.core.parsers.scripts; package org.parabot.core.parsers.scripts;
import org.parabot.core.Core;
import org.parabot.core.desc.ScriptDescription;
import org.parabot.environment.scripts.executers.ScriptExecuter;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.HashMap; import java.util.HashMap;
import java.util.Map; import java.util.Map;
import java.util.TreeMap; import java.util.TreeMap;
import org.parabot.core.Core;
import org.parabot.core.desc.ScriptDescription;
import org.parabot.environment.scripts.executers.ScriptExecuter;
/** /**
* Abstract class for parsing scripts * Abstract class for parsing scripts
* *
@@ -18,8 +18,6 @@ public abstract class ScriptParser {
public static final Map<ScriptDescription, ScriptExecuter> SCRIPT_CACHE = new HashMap<ScriptDescription, ScriptExecuter>(); public static final Map<ScriptDescription, ScriptExecuter> SCRIPT_CACHE = new HashMap<ScriptDescription, ScriptExecuter>();
public abstract void execute();
public static ScriptDescription[] getDescriptions() { public static ScriptDescription[] getDescriptions() {
SCRIPT_CACHE.clear(); SCRIPT_CACHE.clear();
final ArrayList<ScriptParser> parsers = new ArrayList<ScriptParser>(); final ArrayList<ScriptParser> parsers = new ArrayList<ScriptParser>();
@@ -44,9 +42,11 @@ public abstract class ScriptParser {
Core.verbose("Scripts parsed."); Core.verbose("Scripts parsed.");
} }
Map<ScriptDescription, ScriptExecuter> SORTED_SCRIPT_CACHE = new TreeMap<ScriptDescription, ScriptExecuter>( SCRIPT_CACHE ); Map<ScriptDescription, ScriptExecuter> SORTED_SCRIPT_CACHE = new TreeMap<ScriptDescription, ScriptExecuter>(SCRIPT_CACHE);
return SORTED_SCRIPT_CACHE.keySet().toArray(new ScriptDescription[SORTED_SCRIPT_CACHE.size()]); return SORTED_SCRIPT_CACHE.keySet().toArray(new ScriptDescription[SORTED_SCRIPT_CACHE.size()]);
} }
public abstract void execute();
} }
@@ -1,36 +1,23 @@
package org.parabot.core.parsers.servers; package org.parabot.core.parsers.servers;
import java.io.File;
import java.io.FileReader;
import java.io.FilenameFilter;
import java.io.IOException;
import java.lang.reflect.Constructor;
import java.net.URL;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Objects;
import org.json.simple.JSONObject; import org.json.simple.JSONObject;
import org.json.simple.parser.ParseException; import org.json.simple.parser.ParseException;
import org.parabot.core.Configuration;
import org.parabot.core.Context;
import org.parabot.core.Core; import org.parabot.core.Core;
import org.parabot.core.Directories; import org.parabot.core.Directories;
import org.parabot.core.build.BuildPath;
import org.parabot.core.classpath.ClassPath; import org.parabot.core.classpath.ClassPath;
import org.parabot.core.desc.ServerDescription; import org.parabot.core.desc.ServerDescription;
import org.parabot.core.desc.ServerProviderInfo; import org.parabot.core.desc.ServerProviderInfo;
import org.parabot.core.ui.components.VerboseLoader;
import org.parabot.core.ui.utils.UILog;
import org.parabot.environment.api.utils.WebUtil; import org.parabot.environment.api.utils.WebUtil;
import org.parabot.environment.servers.ServerManifest; import org.parabot.environment.servers.ServerManifest;
import org.parabot.environment.servers.ServerProvider;
import org.parabot.environment.servers.executers.LocalPublicServerExecuter; import org.parabot.environment.servers.executers.LocalPublicServerExecuter;
import org.parabot.environment.servers.executers.LocalServerExecuter; import org.parabot.environment.servers.executers.LocalServerExecuter;
import org.parabot.environment.servers.executers.PublicServerExecuter;
import org.parabot.environment.servers.loader.ServerLoader; import org.parabot.environment.servers.loader.ServerLoader;
import javax.swing.*; import java.io.File;
import java.io.FileReader;
import java.io.IOException;
import java.lang.reflect.Constructor;
import java.util.ArrayList;
/** /**
* Parses local server providers located in the servers directory * Parses local server providers located in the servers directory
@@ -86,24 +73,24 @@ public class LocalServers extends ServerParser {
} }
} }
for (File file : Directories.listJSONFiles(Directories.getServerPath())){ for (File file : Directories.listJSONFiles(Directories.getServerPath())) {
Core.verbose("[Local server in]: " + file.getName()); Core.verbose("[Local server in]: " + file.getName());
try { try {
JSONObject object = (JSONObject) WebUtil.getJsonParser().parse(new FileReader(file)); JSONObject object = (JSONObject) WebUtil.getJsonParser().parse(new FileReader(file));
String name = (String) object.get("name"); String name = (String) object.get("name");
String author = (String) object.get("author"); String author = (String) object.get("author");
double version = (Double) object.get("version"); double version = (Double) object.get("version");
String clientClass = (String) object.get("client-class"); String clientClass = (String) object.get("client-class");
Object bank; Object bank;
int bankTabs = 0; int bankTabs = 0;
if ((bank = object.get("bank")) != null){ if ((bank = object.get("bank")) != null) {
bankTabs = (int) bank; bankTabs = (int) bank;
} }
JSONObject locations = (JSONObject) object.get("locations"); JSONObject locations = (JSONObject) object.get("locations");
String server = (String) locations.get("server"); String server = (String) locations.get("server");
String provider = (String) locations.get("provider"); String provider = (String) locations.get("provider");
String hooks = (String) locations.get("hooks"); String hooks = (String) locations.get("hooks");
Core.verbose("[Local server]: " + name); Core.verbose("[Local server]: " + name);
ServerProviderInfo serverProviderInfo = new ServerProviderInfo(server, hooks, name, clientClass, bankTabs); ServerProviderInfo serverProviderInfo = new ServerProviderInfo(server, hooks, name, clientClass, bankTabs);
@@ -43,9 +43,9 @@ public class PublicServers extends ServerParser {
while ((line = br.readLine()) != null) { while ((line = br.readLine()) != null) {
JSONObject jsonObject = (JSONObject) parser.parse(line); JSONObject jsonObject = (JSONObject) parser.parse(line);
String name = String.valueOf(jsonObject.get("name")); String name = String.valueOf(jsonObject.get("name"));
String author = String.valueOf(jsonObject.get("author")); String author = String.valueOf(jsonObject.get("author"));
double version = Double.parseDouble(String.valueOf(jsonObject.get("version"))); double version = Double.parseDouble(String.valueOf(jsonObject.get("version")));
ServerDescription desc = new ServerDescription(name, ServerDescription desc = new ServerDescription(name,
author, version); author, version);
@@ -17,8 +17,6 @@ import java.util.TreeMap;
public abstract class ServerParser { public abstract class ServerParser {
public static final Map<ServerDescription, ServerExecuter> SERVER_CACHE = new HashMap<ServerDescription, ServerExecuter>(); public static final Map<ServerDescription, ServerExecuter> SERVER_CACHE = new HashMap<ServerDescription, ServerExecuter>();
public abstract void execute();
public static final ServerDescription[] getDescriptions() { public static final ServerDescription[] getDescriptions() {
SERVER_CACHE.clear(); SERVER_CACHE.clear();
final ArrayList<ServerParser> parsers = new ArrayList<>(); final ArrayList<ServerParser> parsers = new ArrayList<>();
@@ -43,9 +41,11 @@ public abstract class ServerParser {
Core.verbose("Server providers parsed."); Core.verbose("Server providers parsed.");
} }
Map<ServerDescription, ServerExecuter> SORTED_SERVER_CACHE = new TreeMap<ServerDescription, ServerExecuter>( SERVER_CACHE ); Map<ServerDescription, ServerExecuter> SORTED_SERVER_CACHE = new TreeMap<ServerDescription, ServerExecuter>(SERVER_CACHE);
return SORTED_SERVER_CACHE.keySet().toArray(new ServerDescription[SORTED_SERVER_CACHE.size()]); return SORTED_SERVER_CACHE.keySet().toArray(new ServerDescription[SORTED_SERVER_CACHE.size()]);
} }
public abstract void execute();
} }
@@ -9,324 +9,321 @@ import java.util.ArrayList;
import java.util.Arrays; import java.util.Arrays;
/** /**
*
* A <code>RefClass</code> represents a class or an instance of that class, if * A <code>RefClass</code> represents a class or an instance of that class, if
* no instance is provided this class can only get values from static fields and * no instance is provided this class can only get values from static fields and
* only invoke static methods * only invoke static methods
* *
* @author Everel * @author Everel
*
*/ */
public class RefClass extends RefModifiers { public class RefClass extends RefModifiers {
private Object instance; private Object instance;
private Class<?> clazz; private Class<?> clazz;
public RefClass(Class<?> clazz) { public RefClass(Class<?> clazz) {
this(clazz, null); this(clazz, null);
} }
public RefClass(Object instance) { public RefClass(Object instance) {
this(instance.getClass(), instance); this(instance.getClass(), instance);
} }
public RefClass(Class<?> clazz, Object instance) { public RefClass(Class<?> clazz, Object instance) {
super(clazz.getModifiers()); super(clazz.getModifiers());
this.clazz = clazz; this.clazz = clazz;
setInstance(instance); setInstance(instance);
} }
/** /**
* Sets the instance of this class so now non static fields values can be * Gets the instance of this class
* retrieved and non static methods can be invoked *
* * @return if an instance of this class is known it will return that
* @param instance * instance, otherwise it will return null.
* instance of this class. */
*/ public Object getInstance() {
public void setInstance(Object instance) { return this.instance;
if (instance == null) { }
this.instance = null;
return;
}
if (this.clazz != null) {
if (!clazz.isInstance(instance)) {
throw new IllegalArgumentException(instance
+ " is not an instance of the class " + clazz);
}
}
this.instance = instance;
}
/** /**
* Gets the instance of this class * Sets the instance of this class so now non static fields values can be
* * retrieved and non static methods can be invoked
* @return if an instance of this class is known it will return that *
* instance, otherwise it will return null. * @param instance instance of this class.
*/ */
public Object getInstance() { public void setInstance(Object instance) {
return this.instance; if (instance == null) {
} this.instance = null;
return;
}
if (this.clazz != null) {
if (!clazz.isInstance(instance)) {
throw new IllegalArgumentException(instance
+ " is not an instance of the class " + clazz);
}
}
this.instance = instance;
}
/** /**
* Gets the class which this RefClass is representing * Gets the class which this RefClass is representing
* *
* @return class which this RefClass is representing * @return class which this RefClass is representing
*/ */
public Class<?> getRepresentingClass() { public Class<?> getRepresentingClass() {
return this.clazz; return this.clazz;
} }
public String getClassName() { public String getClassName() {
return this.clazz.getName(); return this.clazz.getName();
} }
public String getSimpleName() { public String getSimpleName() {
return this.clazz.getSimpleName(); return this.clazz.getSimpleName();
} }
public String getCanonicalName() { public String getCanonicalName() {
return this.clazz.getCanonicalName(); return this.clazz.getCanonicalName();
} }
public Annotation[] getAnnotations(){ public Annotation[] getAnnotations() {
return this.clazz.getAnnotations(); return this.clazz.getAnnotations();
} }
/** /**
* Gets the type of this class * Gets the type of this class
* *
* @return type of this class * @return type of this class
*/ */
public org.objectweb.asm.Type getASMType() { public org.objectweb.asm.Type getASMType() {
return org.objectweb.asm.Type.getType(this.clazz); return org.objectweb.asm.Type.getType(this.clazz);
} }
/** /**
* Gets the class' fields * Gets the class' fields
* *
* @return all fields if an instance is provided, otherwise only static * @return all fields if an instance is provided, otherwise only static
* fields * fields
*/ */
public RefField[] getFields() { public RefField[] getFields() {
ArrayList<RefField> fields = new ArrayList<RefField>(); ArrayList<RefField> fields = new ArrayList<RefField>();
// add all static fields // add all static fields
for (Field f : clazz.getDeclaredFields()) { for (Field f : clazz.getDeclaredFields()) {
if (Modifier.isStatic(f.getModifiers())) { if (Modifier.isStatic(f.getModifiers())) {
fields.add(new RefField(f, instance)); fields.add(new RefField(f, instance));
} }
} }
if (this.instance != null) { if (this.instance != null) {
// add all non static fields // add all non static fields
for (Field f : clazz.getDeclaredFields()) { for (Field f : clazz.getDeclaredFields()) {
if (!Modifier.isStatic(f.getModifiers())) { if (!Modifier.isStatic(f.getModifiers())) {
fields.add(new RefField(f, instance)); fields.add(new RefField(f, instance));
} }
} }
} }
return fields.toArray(new RefField[fields.size()]); return fields.toArray(new RefField[fields.size()]);
} }
/** /**
* Determines if a object is an instance of this class * Determines if a object is an instance of this class
* @param object the object you want to check *
* @return <code>true</code> if the object is an instance of this class; <code>false</code> otherwise * @param object the object you want to check
*/ *
public boolean instanceOf(Object object) { * @return <code>true</code> if the object is an instance of this class; <code>false</code> otherwise
return this.clazz.isInstance(object); */
} public boolean instanceOf(Object object) {
return this.clazz.isInstance(object);
}
/** /**
* Gets field by field name * Gets field by field name
* *
* @param name * @param name name of the field
* name of the field *
* @return the field if found * @return the field if found
*/ */
public RefField getField(String name) { public RefField getField(String name) {
return getField(name, null); return getField(name, null);
} }
/** /**
* Gets field by field name and desc * Gets field by field name and desc
* *
* @param name * @param name name of the field
* name of the field * @param desc desc type of the field
* @param desc *
* desc type of the field * @return the field if found
* @return the field if found */
*/ public RefField getField(String name, String desc) {
public RefField getField(String name, String desc) { RefField[] fields = getFields();
RefField[] fields = getFields(); for (RefField f : fields) {
for (RefField f : fields) { if (f.getName().equals(name)) {
if (f.getName().equals(name)) { if (desc == null) {
if (desc == null) { return f;
return f; }
} if (desc.equals(f.getTypeDesc())) {
if (desc.equals(f.getTypeDesc())) { return f;
return f; }
} }
} }
} return null;
return null; }
}
/** /**
* Determines if this class has a super class * Determines if this class has a super class
* *
* @return <code>true</code> if this class has a super class and which is * @return <code>true</code> if this class has a super class and which is
* not the java/lang/Object class, otherwise <code>false.</code> * not the java/lang/Object class, otherwise <code>false.</code>
*/ */
public boolean hasSuperclass() { public boolean hasSuperclass() {
return hasSuperclass(true); return hasSuperclass(true);
} }
/** /**
* Determines if this class has a super class * Determines if this class has a super class
* *
* @param ignoreObjectClass * @param ignoreObjectClass if you want this method to return false when the superclass is
* if you want this method to return false when the superclass is * the java/lang/Object class
* the java/lang/Object class *
* @return <code>true</code> if this class has a superclass, otherwise * @return <code>true</code> if this class has a superclass, otherwise
* <code>false</code> * <code>false</code>
*/ */
public boolean hasSuperclass(boolean ignoreObjectClass) { public boolean hasSuperclass(boolean ignoreObjectClass) {
if (!ignoreObjectClass) { if (!ignoreObjectClass) {
return !clazz.equals(Object.class); return !clazz.equals(Object.class);
} }
Class<?> superClass = clazz.getSuperclass(); Class<?> superClass = clazz.getSuperclass();
if(superClass == null) { if (superClass == null) {
return false; return false;
} }
return !superClass.equals(Object.class); return !superClass.equals(Object.class);
} }
/** /**
* Returns a new RefClass representing the superclass of this RefClass * Returns a new RefClass representing the superclass of this RefClass
* *
* @return superclass of this RefClass * @return superclass of this RefClass
*/ */
public RefClass getSuperclass() { public RefClass getSuperclass() {
return new RefClass(clazz.getSuperclass(), instance); return new RefClass(clazz.getSuperclass(), instance);
} }
/** /**
* Creates a new instance of this class * Creates a new instance of this class
* *
* @return a RefClass representing a fresh created instance of that class * @return a RefClass representing a fresh created instance of that class
*/ */
public RefClass newInstance() { public RefClass newInstance() {
try { try {
return new RefClass(clazz.newInstance()); return new RefClass(clazz.newInstance());
} catch (Throwable t) { } catch (Throwable t) {
t.printStackTrace(); t.printStackTrace();
} }
return null; return null;
} }
/** /**
* Gets the empty (without parameters) constructor of this class if any * Gets the empty (without parameters) constructor of this class if any
* *
* @return empty constructor if there, otherwise <code>null</code> * @return empty constructor if there, otherwise <code>null</code>
*/ */
public RefConstructor getConstructor() { public RefConstructor getConstructor() {
return getConstructor(new Class<?>[] {}); return getConstructor(new Class<?>[]{});
} }
/** /**
* Gets a RefConstructor from this class * Gets a RefConstructor from this class
* *
* @param parameters * @param parameters the constructor it's parameters
* the constructor it's parameters *
* @return the retrieved constructor * @return the retrieved constructor
*/ */
public RefConstructor getConstructor(Class<?>[] parameters) { public RefConstructor getConstructor(Class<?>[] parameters) {
try { try {
return new RefConstructor(clazz.getDeclaredConstructor(parameters)); return new RefConstructor(clazz.getDeclaredConstructor(parameters));
} catch (Throwable t) { } catch (Throwable t) {
t.printStackTrace(); t.printStackTrace();
} }
return null; return null;
} }
/** /**
* Gets all constructors of this class * Gets all constructors of this class
* *
* @return an array with all the constructors in this class * @return an array with all the constructors in this class
*/ */
public RefConstructor[] getConstructors() { public RefConstructor[] getConstructors() {
Constructor<?>[] constructors = clazz.getDeclaredConstructors(); Constructor<?>[] constructors = clazz.getDeclaredConstructors();
RefConstructor[] refConstructors = new RefConstructor[constructors.length]; RefConstructor[] refConstructors = new RefConstructor[constructors.length];
for (int i = 0; i < constructors.length; i++) { for (int i = 0; i < constructors.length; i++) {
refConstructors[i] = new RefConstructor(constructors[i]); refConstructors[i] = new RefConstructor(constructors[i]);
} }
return refConstructors; return refConstructors;
} }
/** /**
* Gets the class' methods * Gets the class' methods
* *
* @return all methods if an instance is provided, otherwise only static * @return all methods if an instance is provided, otherwise only static
* methods * methods
*/ */
public RefMethod[] getMethods() { public RefMethod[] getMethods() {
ArrayList<RefMethod> methods = new ArrayList<RefMethod>(); ArrayList<RefMethod> methods = new ArrayList<RefMethod>();
// add all static methods // add all static methods
for (Method m : clazz.getDeclaredMethods()) { for (Method m : clazz.getDeclaredMethods()) {
if (Modifier.isStatic(m.getModifiers())) { if (Modifier.isStatic(m.getModifiers())) {
methods.add(new RefMethod(m, instance)); methods.add(new RefMethod(m, instance));
} }
} }
if (this.instance != null) { if (this.instance != null) {
// add all non static methods // add all non static methods
for (Method m : clazz.getDeclaredMethods()) { for (Method m : clazz.getDeclaredMethods()) {
if (!Modifier.isStatic(m.getModifiers())) { if (!Modifier.isStatic(m.getModifiers())) {
methods.add(new RefMethod(m, instance)); methods.add(new RefMethod(m, instance));
} }
} }
} }
return methods.toArray(new RefMethod[methods.size()]); return methods.toArray(new RefMethod[methods.size()]);
} }
/** /**
* Finds and returns the first RefMethod match with given method name * Finds and returns the first RefMethod match with given method name
* *
* @param name * @param name method its name
* method its name *
* @return the first match, or if not found <code>null</code> * @return the first match, or if not found <code>null</code>
*/ */
public RefMethod getMethod(String name) { public RefMethod getMethod(String name) {
return getMethod(name, null); return getMethod(name, null);
} }
/** /**
* Finds a RefMethod in this RefClass * Finds a RefMethod in this RefClass
* *
* @param name * @param name the method its name
* the method its name * @param parameters the method its parameters
* @param parameters *
* the method its parameters * @return the matched method or if not found null <code>null</code>
* @return the matched method or if not found null <code>null</code> */
*/ public RefMethod getMethod(String name, Class<?>[] parameters) {
public RefMethod getMethod(String name, Class<?>[] parameters) { try {
try { for (RefMethod method : getMethods()) {
for (RefMethod method : getMethods()) { if (method.getName().equals(name)) {
if (method.getName().equals(name)) { if (parameters == null || Arrays.equals(method.getParameterTypes(), parameters)) {
if (parameters == null || Arrays.equals(method.getParameterTypes(), parameters)) { return method;
return method; }
} }
} }
} } catch (Throwable t) {
} catch (Throwable t) { t.printStackTrace();
t.printStackTrace(); }
} return null;
return null; }
}
public String toString() { public String toString() {
if (this.instance != null) { if (this.instance != null) {
return new StringBuilder().append(this.instance.toString()) return new StringBuilder().append(this.instance.toString())
.append(" : ").append(this.clazz.toString()).toString(); .append(" : ").append(this.clazz.toString()).toString();
} }
return this.clazz.toString(); return this.clazz.toString();
} }
} }
@@ -3,103 +3,101 @@ package org.parabot.core.reflect;
import java.lang.reflect.Constructor; import java.lang.reflect.Constructor;
/** /**
*
* A <code>RefConstructor</code> class represent a constructor method of a * A <code>RefConstructor</code> class represent a constructor method of a
* <code>RefClass</code>. * <code>RefClass</code>.
* *
* @author Everel * @author Everel
*
*/ */
public class RefConstructor extends RefModifiers { public class RefConstructor extends RefModifiers {
private Constructor<?> constructor; private Constructor<?> constructor;
public RefConstructor(Constructor<?> constructor) { public RefConstructor(Constructor<?> constructor) {
super(constructor.getModifiers()); super(constructor.getModifiers());
this.constructor = constructor; this.constructor = constructor;
} }
/** /**
* Creates a new instance of this class by invoking this constructor * Creates a new instance of this class by invoking this constructor
* *
* @return the instance of the class * @return the instance of the class
*/ */
public RefClass newInstance() { public RefClass newInstance() {
return newInstance(new Object[] {}); return newInstance(new Object[]{});
} }
/** /**
* Creates a new instance of this class by invoking this constructor * Creates a new instance of this class by invoking this constructor
* *
* @param args * @param args the arguments for the constructor
* the arguments for the constructor *
* @return the instance of the class * @return the instance of the class
*/ */
public RefClass newInstance(Object... args) { public RefClass newInstance(Object... args) {
if (!constructor.isAccessible()) { if (!constructor.isAccessible()) {
constructor.setAccessible(true); constructor.setAccessible(true);
} }
try { try {
Object instance = constructor.newInstance(args); Object instance = constructor.newInstance(args);
return new RefClass(instance); return new RefClass(instance);
} catch (Throwable t) { } catch (Throwable t) {
t.printStackTrace(); t.printStackTrace();
} }
return null; return null;
} }
/** /**
* Get the value of the accessible flag for this object. * Get the value of the accessible flag for this object.
* *
* @return the value of the object's accessible flag * @return the value of the object's accessible flag
*/ */
public boolean isAccessible() { public boolean isAccessible() {
return constructor.isAccessible(); return constructor.isAccessible();
} }
/** /**
* Returns <code>true</code> if this constructor is a synthetic constructor; * Returns <code>true</code> if this constructor is a synthetic constructor;
* returns <code>false</code> otherwise. * returns <code>false</code> otherwise.
* *
* @return <code>true</code> if this constructor is a synthetic constructor; * @return <code>true</code> if this constructor is a synthetic constructor;
* returns <code>false</code> otherwise * returns <code>false</code> otherwise
*/ */
public boolean isSynthetic() { public boolean isSynthetic() {
return constructor.isSynthetic(); return constructor.isSynthetic();
} }
/** /**
* Returns the name of the constructor. * Returns the name of the constructor.
* *
* @return name of the constructor * @return name of the constructor
*/ */
public String getName() { public String getName() {
return constructor.getName(); return constructor.getName();
} }
/** /**
* Returns an array of the parameter types of this constructor * Returns an array of the parameter types of this constructor
* *
* @return an array of the parameter types of this constructor * @return an array of the parameter types of this constructor
*/ */
public Class<?>[] getParameterTypes() { public Class<?>[] getParameterTypes() {
return constructor.getParameterTypes(); return constructor.getParameterTypes();
} }
/** /**
* Gets the java reflection API constructor representation * Gets the java reflection API constructor representation
* *
* @return constructor * @return constructor
*/ */
public Constructor<?> getConstructor() { public Constructor<?> getConstructor() {
return this.constructor; return this.constructor;
} }
public String toGenericString() { public String toGenericString() {
return constructor.toGenericString(); return constructor.toGenericString();
} }
public String toString() { public String toString() {
return constructor.toString(); return constructor.toString();
} }
} }
@@ -4,378 +4,366 @@ import java.lang.reflect.Field;
import java.lang.reflect.Type; import java.lang.reflect.Type;
/** /**
*
* A <code>RefField</code> represents a field in a <code>RefClass</code> * A <code>RefField</code> represents a field in a <code>RefClass</code>
* *
* @author Everel * @author Everel
*
*/ */
public class RefField extends RefModifiers { public class RefField extends RefModifiers {
private Field field; private Field field;
private Object instance; private Object instance;
public RefField(Field field) { public RefField(Field field) {
this(field, null); this(field, null);
} }
public RefField(Field field, Object instance) { public RefField(Field field, Object instance) {
super(field.getModifiers()); super(field.getModifiers());
this.field = field; this.field = field;
this.instance = instance; this.instance = instance;
} }
/** /**
* Retrieves the field it's value as object * Retrieves the field it's value as object
* *
* @return the value of the field * @return the value of the field
*/ */
public Object asObject() { public Object asObject() {
if (instance == null && !isStatic()) { if (instance == null && !isStatic()) {
throw new IllegalStateException( throw new IllegalStateException(
"Non static field cannot be fetched without an instance"); "Non static field cannot be fetched without an instance");
} }
try { try {
if (!isAccessible()) { if (!isAccessible()) {
field.setAccessible(true); field.setAccessible(true);
} }
return field.get(instance); return field.get(instance);
} catch (Throwable t) { } catch (Throwable t) {
t.printStackTrace(); t.printStackTrace();
} }
return null; return null;
} }
/** /**
* Retrieves the field value as an integer * Retrieves the field value as an integer
* *
* @return integer value of field * @return integer value of field
*/ */
public int asInt() { public int asInt() {
return (int) asObject(); return (int) asObject();
} }
/** /**
* Retrieves the field value as a long * Retrieves the field value as a long
* *
* @return long value of field * @return long value of field
*/ */
public long asLong() { public long asLong() {
return (long) asObject(); return (long) asObject();
} }
/** /**
* Retrieves the field value as an double * Retrieves the field value as an double
* *
* @return double value of field * @return double value of field
*/ */
public double asDouble() { public double asDouble() {
return (double) asObject(); return (double) asObject();
} }
/** /**
* Retrieves the field value as a float * Retrieves the field value as a float
* *
* @return float value of field * @return float value of field
*/ */
public float asFloat() { public float asFloat() {
return (float) asObject(); return (float) asObject();
} }
/** /**
* Retrieves the field value as a boolean * Retrieves the field value as a boolean
* *
* @return boolean value of field * @return boolean value of field
*/ */
public boolean asBoolean() { public boolean asBoolean() {
return (boolean) asObject(); return (boolean) asObject();
} }
/** /**
* Retrieves the field value as a short * Retrieves the field value as a short
* *
* @return short value of field * @return short value of field
*/ */
public short asShort() { public short asShort() {
return (short) asObject(); return (short) asObject();
} }
/** /**
* Retrieves the field value as a byte * Retrieves the field value as a byte
* *
* @return byte value of field * @return byte value of field
*/ */
public byte asByte() { public byte asByte() {
return (byte) asObject(); return (byte) asObject();
} }
/** /**
* Retrieves the field value as a java/lang/String * Retrieves the field value as a java/lang/String
* *
* @return String value of field * @return String value of field
*/ */
public String asString() { public String asString() {
return (String) asObject(); return (String) asObject();
} }
/** /**
* Retrieves the field value as a character * Retrieves the field value as a character
* *
* @return char value of field * @return char value of field
*/ */
public char asChar() { public char asChar() {
return (char) asObject(); return (char) asObject();
} }
/** /**
* Sets the field value * Sets the field value
* *
* @param object * @param object object to set
* object to set */
*/ public void set(Object object) {
public void set(Object object) { if (instance == null && !isStatic()) {
if (instance == null && !isStatic()) { throw new IllegalStateException(
throw new IllegalStateException( "Non static field cannot be set without an instance");
"Non static field cannot be set without an instance"); }
} if (!field.isAccessible()) {
if (!field.isAccessible()) { field.setAccessible(true);
field.setAccessible(true); }
} try {
try { field.set(instance, object);
field.set(instance, object); } catch (Throwable t) {
} catch (Throwable t) { t.printStackTrace();
t.printStackTrace(); }
} }
}
/** /**
* Sets the field integer value * Sets the field integer value
* *
* @param i * @param i value to set
* value to set */
*/ public void setInt(int i) {
public void setInt(int i) { set(i);
set(i); }
}
/** /**
* Sets the field long value * Sets the field long value
* *
* @param l * @param l value to set
* value to set */
*/ public void setLong(long l) {
public void setLong(long l) { set(l);
set(l); }
}
/** /**
* Sets the field double value * Sets the field double value
* *
* @param d * @param d value to set
* value to set */
*/ public void setDouble(double d) {
public void setDouble(double d) { set(d);
set(d); }
}
/** /**
* Sets the field float value * Sets the field float value
* *
* @param f * @param f value to set
* value to set */
*/ public void setFloat(float f) {
public void setFloat(float f) { set(f);
set(f); }
}
/** /**
* Sets the field boolean value * Sets the field boolean value
* *
* @param b * @param b value to set
* value to set */
*/ public void setBoolean(boolean b) {
public void setBoolean(boolean b) { set(b);
set(b); }
}
/** /**
* Sets the field short value * Sets the field short value
* *
* @param s * @param s value to set
* value to set */
*/ public void setShort(short s) {
public void setShort(short s) { set(s);
set(s); }
}
/** /**
* Sets the byte integer value * Sets the byte integer value
* *
* @param b * @param b value to set
* value to set */
*/ public void setByte(byte b) {
public void setByte(byte b) { set(b);
set(b); }
}
/** /**
* Sets the field string value * Sets the field char value
* *
* @param s * @param c value to set
* value to set */
*/ public void setChar(char c) {
public void setString(String s) { set(c);
set(s); }
}
/** /**
* Sets the field char value * Gets the field type
* *
* @param c * @return type of field
* value to set */
*/ public Class<?> getType() {
public void setChar(char c) { return field.getType();
set(c); }
}
/** /**
* Gets the field type * Gets the field type
* *
* @return type of field * @return type of field
*/ */
public Class<?> getType() { public org.objectweb.asm.Type getASMType() {
return field.getType(); return org.objectweb.asm.Type.getType(getType());
} }
/** /**
* Gets the field type * Gets the field description
* *
* @return type of field * @return desc of field
*/ */
public org.objectweb.asm.Type getASMType() { public String getTypeDesc() {
return org.objectweb.asm.Type.getType(getType()); return getASMType().getDescriptor();
} }
/** /**
* Gets the field description * Gets the generic type of this field if any
* *
* @return desc of field * @return generic type
*/ */
public String getTypeDesc() { public Type getGenericType() {
return getASMType().getDescriptor(); return field.getGenericType();
} }
/** /**
* Gets the generic type of this field if any * Determines if this field is an array
* *
* @return generic type * @return <code>true</code> if this field is an array (type)
*/ */
public Type getGenericType() { public boolean isArray() {
return field.getGenericType(); return getASMType().getSort() == org.objectweb.asm.Type.ARRAY;
} }
/** /**
* Determines if this field is an array * Returns the number of dimensions of this array type. This method should
* * only be used for an array type.
* @return <code>true</code> if this field is an array (type) *
*/ * @return the number of dimensions of this array type
public boolean isArray() { */
return getASMType().getSort() == org.objectweb.asm.Type.ARRAY; public int getArrayDimensions() {
} return getASMType().getDimensions();
}
/** /**
* Returns the number of dimensions of this array type. This method should * Determines if field type is a primitive type
* only be used for an array type. *
* * @return <code>true</code> if the field is a primitive type, otherwise
* @return the number of dimensions of this array type * <code>false</code>
*/ */
public int getArrayDimensions() { public boolean isPrimitiveType() {
return getASMType().getDimensions(); return RefUtils.isPrimitive(getType());
} }
/** /**
* Determines if field type is a primitive type * Determines if field type is a string type
* *
* @return <code>true</code> if the field is a primitive type, otherwise * @return <code>true</code> if the field type is a string type, otherwise
* <code>false</code> * <code>false</code>
*/ */
public boolean isPrimitiveType() { public boolean isString() {
return RefUtils.isPrimitive(getType()); return getType() == String.class;
} }
/** /**
* Determines if field type is a string type * Sets the field string value
* *
* @return <code>true</code> if the field type is a string type, otherwise * @param s value to set
* <code>false</code> */
*/ public void setString(String s) {
public boolean isString() { set(s);
return getType() == String.class; }
}
/** /**
* Returns <code>true</code> if this field represents an element of an * Returns <code>true</code> if this field represents an element of an
* enumerated type; returns <code>false</code> otherwise. * enumerated type; returns <code>false</code> otherwise.
* *
* @return <code>true</code> if and only if this field represents an element * @return <code>true</code> if and only if this field represents an element
* of an enumerated type. * of an enumerated type.
*/ */
public boolean isEnumConstants() { public boolean isEnumConstants() {
return field.isEnumConstant(); return field.isEnumConstant();
} }
/** /**
* Get the value of the accessible flag for this object. * Get the value of the accessible flag for this object.
* *
* @return the value of the object's accessible flag * @return the value of the object's accessible flag
*/ */
public boolean isAccessible() { public boolean isAccessible() {
return field.isAccessible(); return field.isAccessible();
} }
/** /**
* Returns <code>true</code> if this field is a synthetic field; returns * Returns <code>true</code> if this field is a synthetic field; returns
* <code>false</code> otherwise. * <code>false</code> otherwise.
* *
* @return <code>true</code> if this field is a synthetic field; returns * @return <code>true</code> if this field is a synthetic field; returns
* <code>false</code> otherwise * <code>false</code> otherwise
*/ */
public boolean isSynthetic() { public boolean isSynthetic() {
return field.isSynthetic(); return field.isSynthetic();
} }
/** /**
* Returns the name of the field. * Returns the name of the field.
* *
* @return name of the field * @return name of the field
*/ */
public String getName() { public String getName() {
return field.getName(); return field.getName();
} }
/** /**
* Gets the java reflection API field representation * Gets the java reflection API field representation
* *
* @return field * @return field
*/ */
public Field getField() { public Field getField() {
return field; return field;
} }
/** /**
* Gets the declaring <code>RefClass</code> of this field * Gets the declaring <code>RefClass</code> of this field
* @return <code>RefClass</code> holding this field *
*/ * @return <code>RefClass</code> holding this field
public RefClass getOwner() { */
return new RefClass(field.getDeclaringClass(), instance); public RefClass getOwner() {
} return new RefClass(field.getDeclaringClass(), instance);
}
public String toGenericString() { public String toGenericString() {
return field.toGenericString(); return field.toGenericString();
} }
public String toString() {
return field.toString();
}
public String toString() {
return field.toString();
}
} }
@@ -3,150 +3,147 @@ package org.parabot.core.reflect;
import java.lang.reflect.Method; import java.lang.reflect.Method;
/** /**
*
* A <code>RefMethod</code> class represent a method of a <code>RefClass</code>. * A <code>RefMethod</code> class represent a method of a <code>RefClass</code>.
* *
* @author Everel * @author Everel
*
*/ */
public class RefMethod extends RefModifiers { public class RefMethod extends RefModifiers {
private Method method; private Method method;
private Object instance; private Object instance;
public RefMethod(Method method) { public RefMethod(Method method) {
this(method, null); this(method, null);
} }
public RefMethod(Method method, Object instance) { public RefMethod(Method method, Object instance) {
super(method.getModifiers()); super(method.getModifiers());
this.method = method; this.method = method;
this.instance = instance; this.instance = instance;
} }
/** /**
* Get the value of the accessible flag for this object. * Get the value of the accessible flag for this object.
* *
* @return the value of the object's accessible flag * @return the value of the object's accessible flag
*/ */
public boolean isAccessible() { public boolean isAccessible() {
return method.isAccessible(); return method.isAccessible();
} }
/** /**
* Determines if this method is a bridge method. * Determines if this method is a bridge method.
* *
* @return <code>true</code> if this method is a bridge method, otherwise * @return <code>true</code> if this method is a bridge method, otherwise
* <code>false</code> * <code>false</code>
*/ */
public boolean isBridge() { public boolean isBridge() {
return method.isBridge(); return method.isBridge();
} }
/** /**
* Determines if this method can take a variable amount of arguments * Determines if this method can take a variable amount of arguments
* *
* @return <code>true</code> if this method can take a variable amount of * @return <code>true</code> if this method can take a variable amount of
* arguments * arguments
*/ */
public boolean isVarArgs() { public boolean isVarArgs() {
return method.isVarArgs(); return method.isVarArgs();
} }
/** /**
* Returns <code>true</code> if this method is a synthetic method; returns * Returns <code>true</code> if this method is a synthetic method; returns
* <code>false</code> otherwise. * <code>false</code> otherwise.
* *
* @return <code>true</code> if this method is a synthetic method; returns * @return <code>true</code> if this method is a synthetic method; returns
* <code>false</code> otherwise * <code>false</code> otherwise
*/ */
public boolean isSynthetic() { public boolean isSynthetic() {
return method.isSynthetic(); return method.isSynthetic();
} }
/** /**
* Returns the name of the method. * Returns the name of the method.
* *
* @return name of the method * @return name of the method
*/ */
public String getName() { public String getName() {
return method.getName(); return method.getName();
} }
/** /**
* Returns an array of the parameter types of this method * Returns an array of the parameter types of this method
* *
* @return an array of the parameter types of this method * @return an array of the parameter types of this method
*/ */
public Class<?>[] getParameterTypes() { public Class<?>[] getParameterTypes() {
return method.getParameterTypes(); return method.getParameterTypes();
} }
/** /**
* Gets the return type of this class * Gets the return type of this class
* *
* @return return type of this class * @return return type of this class
*/ */
public Class<?> getReturnType() { public Class<?> getReturnType() {
return method.getReturnType(); return method.getReturnType();
} }
/** /**
* Gets the return type of this class * Gets the return type of this class
* *
* @return return type of this class * @return return type of this class
*/ */
public org.objectweb.asm.Type getASMReturnType() { public org.objectweb.asm.Type getASMReturnType() {
return org.objectweb.asm.Type.getType(getReturnType()); return org.objectweb.asm.Type.getType(getReturnType());
} }
/** /**
* Gets the java reflection API method representation * Gets the java reflection API method representation
* *
* @return constructor * @return constructor
*/ */
public Method getMethod() { public Method getMethod() {
return this.method; return this.method;
} }
/** /**
* Invokes the method and returns it returned object * Invokes the method and returns it returned object
* *
* @return object returned by the method * @return object returned by the method
*/ */
public Object invoke() { public Object invoke() {
return invoke(new Object[] {}); return invoke(new Object[]{});
} }
/** /**
* * Invokes the method and returns it returned object
* Invokes the method and returns it returned object *
* * @param args arguments for the invokable method
* @param args *
* arguments for the invokable method * @return object returned by the method
* @return object returned by the method */
*/ public Object invoke(Object... args) {
public Object invoke(Object... args) { if (!isStatic() && instance == null) {
if (!isStatic() && instance == null) { throw new IllegalStateException(
throw new IllegalStateException( "Can not invoke non static method without an instance.");
"Can not invoke non static method without an instance."); }
} if (!isAccessible()) {
if(!isAccessible()) { method.setAccessible(true);
method.setAccessible(true); }
} try {
try { Object retObject = method.invoke(instance, args);
Object retObject = method.invoke(instance, args); return retObject;
return retObject; } catch (Throwable t) {
} catch (Throwable t) { t.printStackTrace();
t.printStackTrace(); }
} return null;
return null; }
}
public String toGenericString() { public String toGenericString() {
return method.toGenericString(); return method.toGenericString();
} }
public String toString() { public String toString() {
return method.toString(); return method.toString();
} }
} }
@@ -3,75 +3,73 @@ package org.parabot.core.reflect;
import java.lang.reflect.Modifier; import java.lang.reflect.Modifier;
/** /**
*
* @author Everel * @author Everel
*
*/ */
public class RefModifiers { public class RefModifiers {
private int modifiers; private int modifiers;
public RefModifiers() { public RefModifiers() {
} }
public RefModifiers(int modifiers) { public RefModifiers(int modifiers) {
setModifiers(modifiers); setModifiers(modifiers);
} }
public void setModifiers(int modifiers) { public int getModifiers() {
this.modifiers = modifiers; return this.modifiers;
} }
public int getModifiers() { public void setModifiers(int modifiers) {
return this.modifiers; this.modifiers = modifiers;
} }
public boolean isStatic() { public boolean isStatic() {
return Modifier.isStatic(modifiers); return Modifier.isStatic(modifiers);
} }
public boolean isAbstract() { public boolean isAbstract() {
return Modifier.isAbstract(modifiers); return Modifier.isAbstract(modifiers);
} }
public boolean isFinal() { public boolean isFinal() {
return Modifier.isFinal(modifiers); return Modifier.isFinal(modifiers);
} }
public boolean isInterface() { public boolean isInterface() {
return Modifier.isInterface(modifiers); return Modifier.isInterface(modifiers);
} }
public boolean isNative() { public boolean isNative() {
return Modifier.isNative(modifiers); return Modifier.isNative(modifiers);
} }
public boolean isPrivate() { public boolean isPrivate() {
return Modifier.isPrivate(modifiers); return Modifier.isPrivate(modifiers);
} }
public boolean isProtected() { public boolean isProtected() {
return Modifier.isProtected(modifiers); return Modifier.isProtected(modifiers);
} }
public boolean isPublic() { public boolean isPublic() {
return Modifier.isPublic(modifiers); return Modifier.isPublic(modifiers);
} }
public boolean isStrict() { public boolean isStrict() {
return Modifier.isStrict(modifiers); return Modifier.isStrict(modifiers);
} }
public boolean isSynchronized() { public boolean isSynchronized() {
return Modifier.isSynchronized(modifiers); return Modifier.isSynchronized(modifiers);
} }
public boolean isTransient() { public boolean isTransient() {
return Modifier.isTransient(modifiers); return Modifier.isTransient(modifiers);
} }
public boolean isVolatile() { public boolean isVolatile() {
return Modifier.isVolatile(modifiers); return Modifier.isVolatile(modifiers);
} }
} }
@@ -5,19 +5,17 @@ import java.util.HashSet;
import java.util.Set; import java.util.Set;
/** /**
*
* @author Everel * @author Everel
*
*/ */
public class RefUtils { public class RefUtils {
public static final Set<Class<?>> PRIMITIVE_TYPES = new HashSet<Class<?>>( public static final Set<Class<?>> PRIMITIVE_TYPES = new HashSet<Class<?>>(
Arrays.asList(Boolean.class, Character.class, Byte.class, Arrays.asList(Boolean.class, Character.class, Byte.class,
Short.class, Integer.class, Long.class, Float.class, Short.class, Integer.class, Long.class, Float.class,
Double.class, Void.class)); Double.class, Void.class));
public static boolean isPrimitive(Class<?> clazz) { public static boolean isPrimitive(Class<?> clazz) {
return PRIMITIVE_TYPES.contains(clazz); return PRIMITIVE_TYPES.contains(clazz);
} }
} }
@@ -1,68 +1,64 @@
package org.parabot.core.ui; package org.parabot.core.ui;
import java.awt.Color;
import java.awt.Dimension;
import javax.swing.JDialog;
import org.parabot.core.ui.components.PaintComponent; import org.parabot.core.ui.components.PaintComponent;
import org.parabot.environment.OperatingSystem; import org.parabot.environment.OperatingSystem;
import javax.swing.*;
import java.awt.*;
/** /**
*
* @author Everel * @author Everel
*
*/ */
public class BotDialog extends JDialog { public class BotDialog extends JDialog {
private static final long serialVersionUID = 521800552287194673L; private static final long serialVersionUID = 521800552287194673L;
private static BotDialog instance; private static BotDialog instance;
private BotDialog(BotUI botUI) { private BotDialog(BotUI botUI) {
super(botUI); super(botUI);
botUI.setDialog(this); botUI.setDialog(this);
setUndecorated(true); setUndecorated(true);
getRootPane().setOpaque(false); getRootPane().setOpaque(false);
if (!OperatingSystem.getOS().equals(OperatingSystem.OTHER)) { if (!OperatingSystem.getOS().equals(OperatingSystem.OTHER)) {
try { try {
setBackground(new Color(0, 0, 0, 0)); setBackground(new Color(0, 0, 0, 0));
} catch (UnsupportedOperationException e) { } catch (UnsupportedOperationException e) {
//My "fix" for the perpixel errors some user have when using VPSes //My "fix" for the perpixel errors some user have when using VPSes
if (e.getMessage().contains("PERPIXEL_TRANS")) { if (e.getMessage().contains("PERPIXEL_TRANS")) {
System.err System.err
.println("WARNING: We were unable to set a translucent background!" .println("WARNING: We were unable to set a translucent background!"
+ "\n\tThis generally occurs with old/outdated graphics drivers. Please consider updating them if possible." + "\n\tThis generally occurs with old/outdated graphics drivers. Please consider updating them if possible."
+ "\n\tParabot will still attempt to run, however some GUI elements may or may not function."); + "\n\tParabot will still attempt to run, however some GUI elements may or may not function.");
} }
} }
} }
setFocusableWindowState(true); setFocusableWindowState(true);
setPreferredSize(botUI.getSize()); setPreferredSize(botUI.getSize());
setSize(botUI.getSize()); setSize(botUI.getSize());
setVisible(true); setVisible(true);
setContentPane(PaintComponent.getInstance(botUI.getSize())); setContentPane(PaintComponent.getInstance(botUI.getSize()));
botUI.setVisible(true); botUI.setVisible(true);
} }
public void setDimensions(Dimension dimension) { public static BotDialog getInstance(BotUI botUI) {
setUndecorated(true); return instance == null ? instance = new BotDialog(botUI) : instance;
getRootPane().setOpaque(false); }
setBackground(new Color(0, 0, 0, 0));
setFocusableWindowState(true);
setPreferredSize(dimension);
setSize(dimension);
setVisible(true);
setContentPane(PaintComponent.getInstance());
PaintComponent.getInstance().setDimensions(dimension);
}
public static BotDialog getInstance(BotUI botUI) { public static BotDialog getInstance() {
return instance == null ? instance = new BotDialog(botUI) : instance; return getInstance(null);
} }
public static BotDialog getInstance() { public void setDimensions(Dimension dimension) {
return getInstance(null); setUndecorated(true);
} getRootPane().setOpaque(false);
setBackground(new Color(0, 0, 0, 0));
setFocusableWindowState(true);
setPreferredSize(dimension);
setSize(dimension);
setVisible(true);
setContentPane(PaintComponent.getInstance());
PaintComponent.getInstance().setDimensions(dimension);
}
} }
+16 -16
View File
@@ -31,15 +31,14 @@ import java.util.ArrayList;
public class BotUI extends JFrame implements ActionListener, ComponentListener, WindowListener { public class BotUI extends JFrame implements ActionListener, ComponentListener, WindowListener {
private static final long serialVersionUID = -2126184292879805519L; private static final long serialVersionUID = -2126184292879805519L;
private static BotUI instance; private static BotUI instance;
private static JDialog dialog; private static JDialog dialog;
private JMenuBar menuBar; private JMenuBar menuBar;
private JMenu features, scripts, file; private JMenu features, scripts, file;
private JMenuItem run, pause, stop, cacheClear, notifications; private JMenuItem run, pause, stop, cacheClear, notifications;
private boolean runScript, pauseScript; private boolean runScript, pauseScript;
public BotUI(String username, String password) { public BotUI(String username, String password) {
if (instance != null) { if (instance != null) {
throw new IllegalStateException("BotUI already created"); throw new IllegalStateException("BotUI already created");
@@ -75,7 +74,6 @@ public class BotUI extends JFrame implements ActionListener, ComponentListener,
return instance; return instance;
} }
private void createMenu() { private void createMenu() {
menuBar = new JMenuBar(); menuBar = new JMenuBar();
@@ -84,17 +82,17 @@ public class BotUI extends JFrame implements ActionListener, ComponentListener,
features = new JMenu("Features"); features = new JMenu("Features");
JMenuItem screenshot = new JMenuItem("Create screenshot"); JMenuItem screenshot = new JMenuItem("Create screenshot");
JMenuItem proxy = new JMenuItem("Network"); JMenuItem proxy = new JMenuItem("Network");
JMenuItem randoms = new JMenuItem("Randoms"); JMenuItem randoms = new JMenuItem("Randoms");
JMenuItem dialog = new JCheckBoxMenuItem("Disable dialog"); JMenuItem dialog = new JCheckBoxMenuItem("Disable dialog");
JMenuItem logger = new JCheckBoxMenuItem("Logger"); JMenuItem logger = new JCheckBoxMenuItem("Logger");
if (!OperatingSystem.getOS().equals(OperatingSystem.WINDOWS)) { if (!OperatingSystem.getOS().equals(OperatingSystem.WINDOWS)) {
dialog.setSelected(true); dialog.setSelected(true);
} }
JMenuItem explorer = new JMenuItem("Reflection explorer"); JMenuItem explorer = new JMenuItem("Reflection explorer");
JMenuItem exit = new JMenuItem("Exit"); JMenuItem exit = new JMenuItem("Exit");
run = new JMenuItem("Run"); run = new JMenuItem("Run");
run.setIcon(new ImageIcon(Images.getResource("/storage/images/run.png"))); run.setIcon(new ImageIcon(Images.getResource("/storage/images/run.png")));
@@ -146,7 +144,6 @@ public class BotUI extends JFrame implements ActionListener, ComponentListener,
menuBar.add(scripts); menuBar.add(scripts);
menuBar.add(features); menuBar.add(features);
setJMenuBar(menuBar); setJMenuBar(menuBar);
} }
@@ -159,12 +156,15 @@ public class BotUI extends JFrame implements ActionListener, ComponentListener,
switch (command) { switch (command) {
case "Create screenshot": case "Create screenshot":
try { try {
Robot robot = new Robot(); Robot robot = new Robot();
Rectangle parabotScreen = new Rectangle((int) getLocation().getX(), (int) getLocation().getY() + (menuBar.getHeight() + features.getHeight()), getWidth(), getHeight()); int menuBarHeight = menuBar.getHeight() + file.getHeight();
BufferedImage image = robot.createScreenCapture(parabotScreen); Rectangle parabotScreen = new Rectangle(
String randString = StringUtils.randomString(10); (int) getLocation().getX(), (int) getLocation().getY() + menuBarHeight,
boolean search = true; getWidth(), getHeight() - menuBarHeight);
boolean duplicate = false; BufferedImage image = robot.createScreenCapture(parabotScreen);
String randString = StringUtils.randomString(10);
boolean search = true;
boolean duplicate = false;
while (search) { while (search) {
File[] files; File[] files;
if ((files = Directories.getScreenshotDir().listFiles()) != null) { if ((files = Directories.getScreenshotDir().listFiles()) != null) {
+26 -25
View File
@@ -11,14 +11,14 @@ import java.awt.event.ActionListener;
* @author JKetelaar * @author JKetelaar
*/ */
public class Logger extends JPanel { public class Logger extends JPanel {
private static final long serialVersionUID = 1L; private static final long serialVersionUID = 1L;
private static Logger instance; private static Logger instance;
private final DefaultListModel<String> model; private final DefaultListModel<String> model;
private final JList<String> list; private final JList<String> list;
private boolean clearable; private boolean clearable;
private Logger(){ private Logger() {
setLayout(new BorderLayout()); setLayout(new BorderLayout());
list = new JList<>(); list = new JList<>();
@@ -45,34 +45,20 @@ public class Logger extends JPanel {
setVisible(false); setVisible(false);
} }
private ListCellRenderer<? super String> getRenderer() {
return new DefaultListCellRenderer(){
private static final long serialVersionUID = -3589192791360628745L;
@Override
public Component getListCellRendererComponent(JList<?> list,
Object value, int index, boolean isSelected,
boolean cellHasFocus) {
JLabel listCellRendererComponent = (JLabel) super.getListCellRendererComponent(list, value, index, isSelected,cellHasFocus);
listCellRendererComponent.setBorder(BorderFactory.createMatteBorder(0, 0, 1, 0,Color.BLACK));
return listCellRendererComponent;
}
};
}
public static Logger getInstance() { public static Logger getInstance() {
return instance == null ? instance = new Logger() : instance; return instance == null ? instance = new Logger() : instance;
} }
/** /**
* Logs a message in the logger ui * Logs a message in the logger ui
*
* @param message * @param message
* @param uliratha Determines if this should be sent to the uliratha server * @param uliratha Determines if this should be sent to the uliratha server
*/ */
public static void addMessage(String message, boolean uliratha){ public static void addMessage(String message, boolean uliratha) {
instance.model.addElement(message); instance.model.addElement(message);
if (uliratha){ if (uliratha) {
// TODO: Implement latest Uliratha // TODO: Implement latest Uliratha
} }
@@ -80,7 +66,7 @@ public class Logger extends JPanel {
if (last >= 0) { if (last >= 0) {
instance.list.ensureIndexIsVisible(last); instance.list.ensureIndexIsVisible(last);
} }
if (instance.list.getModel().getSize() > 100 && instance.list.getModel().getElementAt(0) != null){ if (instance.list.getModel().getSize() > 100 && instance.list.getModel().getElementAt(0) != null) {
instance.model.remove(0); instance.model.remove(0);
} }
} }
@@ -88,14 +74,29 @@ public class Logger extends JPanel {
/** /**
* @param message * @param message
*/ */
public static void addMessage(String message){ public static void addMessage(String message) {
addMessage(message, true); addMessage(message, true);
} }
protected static void clearLogger(){ protected static void clearLogger() {
instance.model.clear(); instance.model.clear();
} }
private ListCellRenderer<? super String> getRenderer() {
return new DefaultListCellRenderer() {
private static final long serialVersionUID = -3589192791360628745L;
@Override
public Component getListCellRendererComponent(JList<?> list,
Object value, int index, boolean isSelected,
boolean cellHasFocus) {
JLabel listCellRendererComponent = (JLabel) super.getListCellRendererComponent(list, value, index, isSelected, cellHasFocus);
listCellRendererComponent.setBorder(BorderFactory.createMatteBorder(0, 0, 1, 0, Color.BLACK));
return listCellRendererComponent;
}
};
}
public boolean isClearable() { public boolean isClearable() {
return clearable; return clearable;
} }
+120 -123
View File
@@ -17,156 +17,153 @@ import java.io.IOException;
import java.net.URI; import java.net.URI;
/** /**
*
* Users must login with their parabot account through this LoginUI class * Users must login with their parabot account through this LoginUI class
* *
* @author Everel * @author Everel
*
*/ */
public class LoginUI extends JFrame { public class LoginUI extends JFrame {
private static final long serialVersionUID = 2032832552863466297L; private static final long serialVersionUID = 2032832552863466297L;
private static LoginUI instance; private static LoginUI instance;
private static AccountManager manager; private static AccountManager manager;
private JTextField txtUsername; private JTextField txtUsername;
private JPasswordField txtPassword; private JPasswordField txtPassword;
private JButton cmdLogin; private JButton cmdLogin;
private JButton cmdRegister; private JButton cmdRegister;
public LoginUI(String username, String password) {
instance = this;
attempt(username, password);
}
public void attemptLogin() { public LoginUI() {
String username = txtUsername.getText(); instance = this;
String password = new String(txtPassword.getPassword());
if (username.length() > 0 && password.length() > 0) { this.setTitle("Login");
if (manager.login(username, password, false)) { this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
Core.verbose("Logged in."); this.setLocationByPlatform(true);
instance.dispose(); this.setLayout(new BorderLayout());
Core.verbose("Running server selector."); this.setResizable(false);
ServerSelector.getInstance();
} else {
Core.verbose("Failed to log in.");
UILog.log("Error", "Incorrect username or password. Have you tried logging into http://bdn.parabot.org/account/", JOptionPane.ERROR_MESSAGE);
}
}
}
private void attempt(String user, String pass) { SwingUtil.setParabotIcons(this);
Core.verbose("Logging in...");
if (manager.login(user, pass, false)) {
Core.verbose("Logged in.");
instance.dispose();
Core.verbose("Running server selector.");
ServerSelector.getInstance();
} else {
Core.verbose("Failed to log in.");
UILog.log("Error", "Incorrect username or password. Have you tried logging into http://bdn.parabot.org/account/", JOptionPane.ERROR_MESSAGE);
}
} int w = 250;
int x = 8;
int y = 64;
public LoginUI(String username, String password) { JPanel panel = new JPanel() {
instance = this; private static final long serialVersionUID = 2258761648532714183L;
attempt(username, password);
}
public LoginUI() { @Override
instance = this; public void paintComponent(Graphics g) {
super.paintComponent(g);
((Graphics2D) g).setRenderingHint(
RenderingHints.KEY_INTERPOLATION,
RenderingHints.VALUE_INTERPOLATION_BICUBIC);
g.drawImage(Images
.getResource("/storage/images/para.png"),
0, 8, 250, 45, null);
}
};
panel.setLayout(null);
this.setTitle("Login"); txtUsername = new JTextField("");
this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); txtUsername.setBounds(x, y, w - (x << 1), 26);
this.setLocationByPlatform(true); txtUsername.addKeyListener(new KeyAdapter() {
this.setLayout(new BorderLayout()); @Override
this.setResizable(false); public void keyPressed(KeyEvent e) {
if (e.getKeyCode() == 10 || e.getKeyCode() == 13) {
txtPassword.requestFocus();
}
}
});
SwingUtil.setParabotIcons(this); y += 30;
int w = 250; txtPassword = new JPasswordField("");
int x = 8; txtPassword.setBounds(x, y, w - (x << 1), 26);
int y = 64; txtPassword.addKeyListener(new KeyAdapter() {
@Override
public void keyPressed(KeyEvent e) {
if (e.getKeyCode() == 10 || e.getKeyCode() == 13) {
attemptLogin();
}
}
});
JPanel panel = new JPanel() { y += 30;
private static final long serialVersionUID = 2258761648532714183L;
@Override cmdLogin = new JButton("Login");
public void paintComponent(Graphics g) { cmdLogin.addActionListener(new ActionListener() {
super.paintComponent(g); @Override
((Graphics2D) g).setRenderingHint( public void actionPerformed(ActionEvent arg0) {
RenderingHints.KEY_INTERPOLATION, attemptLogin();
RenderingHints.VALUE_INTERPOLATION_BICUBIC); }
g.drawImage(Images });
.getResource("/storage/images/para.png"), cmdLogin.setBounds(x, y, (w - (x << 1)) / 2 - 8, 24);
0, 8, 250, 45, null);
}
};
panel.setLayout(null);
txtUsername = new JTextField(""); cmdRegister = new JButton("Register");
txtUsername.setBounds(x, y, w - (x << 1), 26); cmdRegister.addActionListener(new ActionListener() {
txtUsername.addKeyListener(new KeyAdapter() { @Override
@Override public void actionPerformed(ActionEvent arg0) {
public void keyPressed(KeyEvent e) { URI uri = URI
if (e.getKeyCode() == 10 || e.getKeyCode() == 13) { .create(Configuration.REGISTRATION_PAGE);
txtPassword.requestFocus(); try {
} Desktop.getDesktop().browse(uri);
} } catch (IOException e1) {
}); JOptionPane.showMessageDialog(null, "Connection Error",
"Error", JOptionPane.ERROR_MESSAGE);
e1.printStackTrace();
}
}
});
cmdRegister.setBounds(x + (w - (x << 1)) / 2 + 8, y,
(w - (x << 1)) / 2 - 8, 24);
y += 30; panel.add(txtUsername);
panel.add(txtPassword);
panel.add(cmdLogin);
panel.add(cmdRegister);
txtPassword = new JPasswordField(""); this.add(panel, BorderLayout.CENTER);
txtPassword.setBounds(x, y, w - (x << 1), 26);
txtPassword.addKeyListener(new KeyAdapter() {
@Override
public void keyPressed(KeyEvent e) {
if (e.getKeyCode() == 10 || e.getKeyCode() == 13) {
attemptLogin();
}
}
});
y += 30; this.setVisible(true);
this.requestFocus();
cmdLogin = new JButton("Login"); this.setSize(255, 182);
cmdLogin.addActionListener(new ActionListener() { this.setLocationRelativeTo(null);
@Override
public void actionPerformed(ActionEvent arg0) {
attemptLogin();
}
});
cmdLogin.setBounds(x, y, (w - (x << 1)) / 2 - 8, 24);
cmdRegister = new JButton("Register"); }
cmdRegister.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent arg0) {
URI uri = URI
.create(Configuration.REGISTRATION_PAGE);
try {
Desktop.getDesktop().browse(uri);
} catch (IOException e1) {
JOptionPane.showMessageDialog(null, "Connection Error",
"Error", JOptionPane.ERROR_MESSAGE);
e1.printStackTrace();
}
}
});
cmdRegister.setBounds(x + (w - (x << 1)) / 2 + 8, y,
(w - (x << 1)) / 2 - 8, 24);
panel.add(txtUsername); public void attemptLogin() {
panel.add(txtPassword); String username = txtUsername.getText();
panel.add(cmdLogin); String password = new String(txtPassword.getPassword());
panel.add(cmdRegister);
this.add(panel, BorderLayout.CENTER); if (username.length() > 0 && password.length() > 0) {
if (manager.login(username, password, false)) {
Core.verbose("Logged in.");
instance.dispose();
Core.verbose("Running server selector.");
ServerSelector.getInstance();
} else {
Core.verbose("Failed to log in.");
UILog.log("Error", "Incorrect username or password. Have you tried logging into http://bdn.parabot.org/account/", JOptionPane.ERROR_MESSAGE);
}
}
}
this.setVisible(true); private void attempt(String user, String pass) {
this.requestFocus(); Core.verbose("Logging in...");
if (manager.login(user, pass, false)) {
Core.verbose("Logged in.");
instance.dispose();
Core.verbose("Running server selector.");
ServerSelector.getInstance();
} else {
Core.verbose("Failed to log in.");
UILog.log("Error", "Incorrect username or password. Have you tried logging into http://bdn.parabot.org/account/", JOptionPane.ERROR_MESSAGE);
}
this.setSize(255, 182); }
this.setLocationRelativeTo(null);
}
} }
@@ -27,17 +27,17 @@ public class NetworkUI extends JFrame implements KeyListener, ActionListener,
private static NetworkUI instance; private static NetworkUI instance;
private JComboBox<ProxyType> proxyType; private JComboBox<ProxyType> proxyType;
private JTextField proxyHost; private JTextField proxyHost;
private IntTextField proxyPort; private IntTextField proxyPort;
private JButton submitButton; private JButton submitButton;
private JList<String>[] macList; private JList<String>[] macList;
private JScrollPane[] macScrollList; private JScrollPane[] macScrollList;
private JCheckBox authCheckBox; private JCheckBox authCheckBox;
private JTextField authUsername; private JTextField authUsername;
private JPasswordField authPassword; private JPasswordField authPassword;
private JButton randomize; private JButton randomize;
private NetworkUI() { private NetworkUI() {
initGUI(); initGUI();
@@ -50,8 +50,9 @@ public class NetworkUI extends JFrame implements KeyListener, ActionListener,
@Override @Override
public void setVisible(boolean b) { public void setVisible(boolean b) {
BotUI.getInstance().setEnabled(!b); BotUI.getInstance().setEnabled(!b);
if (ProxySocket.getProxyAddress() != null) if (ProxySocket.getProxyAddress() != null) {
proxyHost.setText(ProxySocket.getProxyAddress().getHostName()); proxyHost.setText(ProxySocket.getProxyAddress().getHostName());
}
proxyPort.setText("" + ProxySocket.getProxyPort()); proxyPort.setText("" + ProxySocket.getProxyPort());
proxyType.setSelectedItem(ProxySocket.getProxyType()); proxyType.setSelectedItem(ProxySocket.getProxyType());
authCheckBox.setSelected(ProxySocket.auth); authCheckBox.setSelected(ProxySocket.auth);
@@ -92,10 +93,10 @@ public class NetworkUI extends JFrame implements KeyListener, ActionListener,
randomize.addActionListener(new ActionListener() { randomize.addActionListener(new ActionListener() {
@Override @Override
public void actionPerformed(ActionEvent e) { public void actionPerformed(ActionEvent e) {
Random rand = new Random(); Random rand = new Random();
byte[] macAddr = new byte[6]; byte[] macAddr = new byte[6];
rand.nextBytes(macAddr); rand.nextBytes(macAddr);
macAddr[0] = (byte)(macAddr[0] & (byte)254); macAddr[0] = (byte) (macAddr[0] & (byte) 254);
for (int i = 0; i < macAddr.length; i++) { for (int i = 0; i < macAddr.length; i++) {
int value = macAddr[i] & 0xFF; int value = macAddr[i] & 0xFF;
macList[i].setSelectedIndex(value); macList[i].setSelectedIndex(value);
@@ -104,7 +105,6 @@ public class NetworkUI extends JFrame implements KeyListener, ActionListener,
} }
}); });
authCheckBox = new JCheckBox("Auth"); authCheckBox = new JCheckBox("Auth");
authCheckBox.setSelected(ProxySocket.auth); authCheckBox.setSelected(ProxySocket.auth);
authCheckBox.addActionListener(this); authCheckBox.addActionListener(this);
@@ -262,9 +262,10 @@ public class NetworkUI extends JFrame implements KeyListener, ActionListener,
.setLogin(username, password); .setLogin(username, password);
byte[] mac = new byte[macList.length]; byte[] mac = new byte[macList.length];
for (int i = 0; i < mac.length; i++) for (int i = 0; i < mac.length; i++) {
mac[i] = (byte) Short.parseShort( mac[i] = (byte) Short.parseShort(
(String) macList[i].getSelectedValue(), 16); (String) macList[i].getSelectedValue(), 16);
}
NetworkInterface.setMac(mac); NetworkInterface.setMac(mac);
try { try {
@@ -277,8 +278,8 @@ public class NetworkUI extends JFrame implements KeyListener, ActionListener,
} }
} }
ProxyType type = (ProxyType) proxyType.getSelectedItem(); ProxyType type = (ProxyType) proxyType.getSelectedItem();
String host = proxyHost.getText(); String host = proxyHost.getText();
int port = proxyPort.getValue(); int port = proxyPort.getValue();
ProxySocket.setProxy(type, host, port); ProxySocket.setProxy(type, host, port);
UILog.log("Info", "Network settings have been set!"); UILog.log("Info", "Network settings have been set!");
@@ -340,8 +341,9 @@ public class NetworkUI extends JFrame implements KeyListener, ActionListener,
public void insertString(int offs, String str, AttributeSet a) public void insertString(int offs, String str, AttributeSet a)
throws BadLocationException { throws BadLocationException {
if (str == null) if (str == null) {
return; return;
}
String oldString = getText(0, getLength()); String oldString = getText(0, getLength());
String newString = oldString.substring(0, offs) + str String newString = oldString.substring(0, offs) + str
+ oldString.substring(offs); + oldString.substring(offs);
@@ -16,7 +16,7 @@ public class RandomUI implements ActionListener {
private static RandomUI instance; private static RandomUI instance;
private JFrame frame; private JFrame frame;
private ArrayList<JCheckBox> checkBoxes; private ArrayList<JCheckBox> checkBoxes;
public static RandomUI getInstance() { public static RandomUI getInstance() {
@@ -27,11 +27,11 @@ import java.util.HashMap;
*/ */
public class ReflectUI extends JFrame { public class ReflectUI extends JFrame {
private static final long serialVersionUID = 98565034137367257L; private static final long serialVersionUID = 98565034137367257L;
private JTree tree; private JTree tree;
private DefaultMutableTreeNode root; private DefaultMutableTreeNode root;
private DefaultTreeModel model; private DefaultTreeModel model;
private JEditorPane basicInfoPane; private JEditorPane basicInfoPane;
private JEditorPane selectionInfoPane; private JEditorPane selectionInfoPane;
private Object instance; private Object instance;
@@ -82,7 +82,7 @@ public class ReflectUI extends JFrame {
@Override @Override
public void actionPerformed(ActionEvent e) { public void actionPerformed(ActionEvent e) {
RefField result = null; RefField result = null;
String search = searchFunction.getText(); String search = searchFunction.getText();
for (RefField f : fields.values()) { for (RefField f : fields.values()) {
if (f != null && (f.asObject()) != null) { if (f != null && (f.asObject()) != null) {
String value; String value;
@@ -103,7 +103,6 @@ public class ReflectUI extends JFrame {
} }
}); });
final JButton adjustClasses = new JButton("Expand"); final JButton adjustClasses = new JButton("Expand");
adjustClasses.addActionListener(new ActionListener() { adjustClasses.addActionListener(new ActionListener() {
@Override @Override
@@ -130,7 +129,6 @@ public class ReflectUI extends JFrame {
searchContent.setMaximumSize(new Dimension(500, (int) searchContent.getPreferredSize().getHeight())); searchContent.setMaximumSize(new Dimension(500, (int) searchContent.getPreferredSize().getHeight()));
searchContent.add(searchButton); searchContent.add(searchButton);
tree = new JTree(); tree = new JTree();
tree.setRootVisible(true); tree.setRootVisible(true);
tree.setShowsRootHandles(true); tree.setShowsRootHandles(true);
@@ -139,9 +137,9 @@ public class ReflectUI extends JFrame {
@Override @Override
public void valueChanged(TreeSelectionEvent event) { public void valueChanged(TreeSelectionEvent event) {
TreePath path = event.getPath(); TreePath path = event.getPath();
Object[] pathElements = path.getPath(); Object[] pathElements = path.getPath();
Object element = pathElements[pathElements.length - 1]; Object element = pathElements[pathElements.length - 1];
if (pathElements.length == 2) { if (pathElements.length == 2) {
setClassInfo(classes.get(element)); setClassInfo(classes.get(element));
} else if (pathElements.length == 3) { } else if (pathElements.length == 3) {
@@ -181,7 +179,7 @@ public class ReflectUI extends JFrame {
content.add(searchContent); content.add(searchContent);
JScrollPane contentPane = new JScrollPane(content); JScrollPane contentPane = new JScrollPane(content);
Dimension prefSize = content.getPreferredSize(); Dimension prefSize = content.getPreferredSize();
contentPane.setPreferredSize(new Dimension(prefSize.width + contentPane.getVerticalScrollBar().getPreferredSize().width, prefSize.height + contentPane.getHorizontalScrollBar().getPreferredSize().height)); contentPane.setPreferredSize(new Dimension(prefSize.width + contentPane.getVerticalScrollBar().getPreferredSize().width, prefSize.height + contentPane.getHorizontalScrollBar().getPreferredSize().height));
setContentPane(contentPane); setContentPane(contentPane);
pack(); pack();
@@ -190,8 +188,8 @@ public class ReflectUI extends JFrame {
} }
private void fillModel() { private void fillModel() {
Context context = Context.getInstance(); Context context = Context.getInstance();
ClassPath classPath = context.getClassPath(); ClassPath classPath = context.getClassPath();
ASMClassLoader classLoader = context.getASMClassLoader(); ASMClassLoader classLoader = context.getASMClassLoader();
for (String className : classPath.classNames) { for (String className : classPath.classNames) {
try { try {
@@ -221,7 +219,7 @@ public class ReflectUI extends JFrame {
} }
private void fillBasicInfoPane() { private void fillBasicInfoPane() {
Context context = Context.getInstance(); Context context = Context.getInstance();
ClassPath classPath = context.getClassPath(); ClassPath classPath = context.getClassPath();
StringBuilder builder = new StringBuilder(); StringBuilder builder = new StringBuilder();
@@ -233,8 +231,8 @@ public class ReflectUI extends JFrame {
} }
private void setFieldInfo(RefField refField) { private void setFieldInfo(RefField refField) {
StringBuilder builder = new StringBuilder(); StringBuilder builder = new StringBuilder();
RefClass refClass = refField.getOwner(); RefClass refClass = refField.getOwner();
builder.append("<h1>").append(refClass.getClassName()).append(".").append(refField.getName()).append("</h1><br/>"); builder.append("<h1>").append(refClass.getClassName()).append(".").append(refField.getName()).append("</h1><br/>");
builder.append("<b>Class: </b>").append(refClass.getClassName()).append("<br/>"); builder.append("<b>Class: </b>").append(refClass.getClassName()).append("<br/>");
builder.append("<b>Value: </b>").append(refField.asObject()).append("<br/>"); builder.append("<b>Value: </b>").append(refField.asObject()).append("<br/>");
@@ -244,7 +242,7 @@ public class ReflectUI extends JFrame {
if (refField.isArray() && refField.getASMType().getClassName().contains("String") && refField.getArrayDimensions() == 1) { if (refField.isArray() && refField.getASMType().getClassName().contains("String") && refField.getArrayDimensions() == 1) {
String[] strings = (String[]) refField.asObject(); String[] strings = (String[]) refField.asObject();
String values = StringUtils.implode(", ", strings); String values = StringUtils.implode(", ", strings);
builder.append("<b>Values: </b>").append(values).append("<br/>"); builder.append("<b>Values: </b>").append(values).append("<br/>");
} }
@@ -23,202 +23,198 @@ import java.net.URLEncoder;
import java.util.HashMap; import java.util.HashMap;
/** /**
*
* Script Selector GUI, shows all scripts * Script Selector GUI, shows all scripts
* *
* @author Everel * @author Everel
*/ */
public final class ScriptSelector extends JFrame { public final class ScriptSelector extends JFrame {
public static ScriptParser parser; private static final long serialVersionUID = 1L;
private static final long serialVersionUID = 1L; public static ScriptParser parser;
private final int WIDTH;
private final int HEIGHT;
private HashMap<String, DefaultMutableTreeNode> categories;
private HashMap<String, ScriptDescription> format;
private DefaultMutableTreeNode root;
private DefaultTreeModel model;
private Font fontCategory = new Font("Arial", Font.BOLD, 12);
private Font fontScript = new Font("Arial", Font.PLAIN, 12);
private JTree tree;
private JEditorPane scriptInfo;
private HashMap<String, DefaultMutableTreeNode> categories; public ScriptSelector() {
private HashMap<String, ScriptDescription> format; this.categories = new HashMap<String, DefaultMutableTreeNode>();
private DefaultMutableTreeNode root; this.format = new HashMap<String, ScriptDescription>();
private DefaultTreeModel model; this.root = new DefaultMutableTreeNode("Scripts");
private final int WIDTH; this.WIDTH = 640;
private final int HEIGHT; this.HEIGHT = 256 + 128;
this.model = new DefaultTreeModel(root);
putScripts();
createUI();
}
public ScriptSelector() { private void runScript(ScriptDescription desc) {
this.categories = new HashMap<String, DefaultMutableTreeNode>(); dispose();
this.format = new HashMap<String, ScriptDescription>(); final ThreadGroup tg = Context.threadGroups.keySet().iterator()
this.root = new DefaultMutableTreeNode("Scripts"); .next();
this.WIDTH = 640; ScriptParser.SCRIPT_CACHE.get(desc).run(tg);
this.HEIGHT = 256 + 128; }
this.model = new DefaultTreeModel(root);
putScripts();
createUI();
}
private void runScript(ScriptDescription desc) { private void putScripts() {
dispose(); final ScriptDescription[] descs = ScriptParser.getDescriptions();
final ThreadGroup tg = Context.threadGroups.keySet().iterator() if (descs == null) {
.next(); return;
ScriptParser.SCRIPT_CACHE.get(desc).run(tg); }
} for (final ScriptDescription scriptDesc : descs) {
if (categories.get(scriptDesc.category) == null) {
DefaultMutableTreeNode cat = new DefaultMutableTreeNode(Category.valueOf(scriptDesc.category.toUpperCase()));
cat.add(new DefaultMutableTreeNode(scriptDesc.scriptName));
root.add(cat);
categories.put(scriptDesc.category, cat);
} else {
categories.get(scriptDesc.category).add(
new DefaultMutableTreeNode(scriptDesc.scriptName));
}
private void putScripts() { format.put(scriptDesc.scriptName, scriptDesc);
final ScriptDescription[] descs = ScriptParser.getDescriptions(); }
if (descs == null) { }
return;
}
for (final ScriptDescription scriptDesc : descs) {
if (categories.get(scriptDesc.category) == null) {
DefaultMutableTreeNode cat = new DefaultMutableTreeNode(Category.valueOf(scriptDesc.category.toUpperCase()));
cat.add(new DefaultMutableTreeNode(scriptDesc.scriptName));
root.add(cat);
categories.put(scriptDesc.category, cat);
} else {
categories.get(scriptDesc.category).add(
new DefaultMutableTreeNode(scriptDesc.scriptName));
}
format.put(scriptDesc.scriptName, scriptDesc); private String getScriptName(String path) {
} return path.split(", ")[2].replaceAll("\\]", "");
} }
private String getServerDesc(final String[] servers) {
if (servers == null) {
return "Unknown";
}
StringBuilder builder = new StringBuilder();
for (int i = 0; i < servers.length; i++) {
builder.append(servers[i]);
if ((i + 1) < servers.length) {
builder.append(", ");
}
}
return builder.toString();
}
private String getScriptName(String path) { private void createUI() {
return path.split(", ")[2].replaceAll("\\]", "");
}
private String getServerDesc(final String[] servers) { this.setTitle("Script Selector");
if (servers == null) { this.setLayout(new BorderLayout());
return "Unknown"; this.setResizable(false);
} this.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
StringBuilder builder = new StringBuilder();
for (int i = 0; i < servers.length; i++) {
builder.append(servers[i]);
if ((i + 1) < servers.length) {
builder.append(", ");
}
}
return builder.toString();
}
private void createUI() { JPanel panel = new JPanel(null);
panel.setPreferredSize(new Dimension(WIDTH, HEIGHT));
this.setTitle("Script Selector"); tree = new JTree();
this.setLayout(new BorderLayout()); tree.setCellRenderer(new ScriptTreeCellRenderer());
this.setResizable(false); tree.setRootVisible(false);
this.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE); tree.setShowsRootHandles(true);
tree.setModel(model);
tree.addTreeSelectionListener(new TreeSelectionListener() {
public void valueChanged(TreeSelectionEvent e) {
String path = e.getPath().toString();
if (path.split(",").length == 3) {
JPanel panel = new JPanel(null); // local scripts
panel.setPreferredSize(new Dimension(WIDTH, HEIGHT)); ScriptDescription def = format.get(getScriptName(e
.getPath().toString()));
if (def != null) {
StringBuilder html = new StringBuilder("<html>");
html.append("<h1><font color=\"black\">")
.append(def.scriptName)
.append("</font></h1><br/>");
html.append("<font color=\"black\"><b>Author: </b>")
.append(def.author).append("</font><br/>");
html.append("<font color=\"black\"><b>Servers: </b>")
.append(getServerDesc(def.servers))
.append("</font><br/>");
html.append("<font color=\"black\"><b>Version: </b>")
.append(def.version).append("</font><br/>");
html.append(
"<font color=\"black\"><b>Description: </b>")
.append(def.description).append("</font><br/>");
html.append("</html>");
scriptInfo.setText(new String(html));
}
tree = new JTree(); }
tree.setCellRenderer(new ScriptTreeCellRenderer()); }
tree.setRootVisible(false); });
tree.setShowsRootHandles(true);
tree.setModel(model);
tree.addTreeSelectionListener(new TreeSelectionListener() {
public void valueChanged(TreeSelectionEvent e) {
String path = e.getPath().toString();
if (path.split(",").length == 3) {
// local scripts scriptInfo = new JEditorPane();
ScriptDescription def = format.get(getScriptName(e scriptInfo.setContentType("text/html");
.getPath().toString())); scriptInfo.setEditable(false);
if (def != null) {
StringBuilder html = new StringBuilder("<html>");
html.append("<h1><font color=\"black\">")
.append(def.scriptName)
.append("</font></h1><br/>");
html.append("<font color=\"black\"><b>Author: </b>")
.append(def.author).append("</font><br/>");
html.append("<font color=\"black\"><b>Servers: </b>")
.append(getServerDesc(def.servers))
.append("</font><br/>");
html.append("<font color=\"black\"><b>Version: </b>")
.append(def.version).append("</font><br/>");
html.append(
"<font color=\"black\"><b>Description: </b>")
.append(def.description).append("</font><br/>");
html.append("</html>");
scriptInfo.setText(new String(html));
}
} JScrollPane scrlScriptTree = new JScrollPane(tree);
} scrlScriptTree.setBounds(4, 4, WIDTH / 2 - 4 - 64, HEIGHT - 4 - 28);
});
scriptInfo = new JEditorPane(); JScrollPane scrlScriptInfo = new JScrollPane(scriptInfo);
scriptInfo.setContentType("text/html"); scrlScriptInfo.setBounds(WIDTH / 2 + 4 - 64, 4, WIDTH / 2 - 8 + 64,
scriptInfo.setEditable(false); HEIGHT - 4 - 28);
JScrollPane scrlScriptTree = new JScrollPane(tree); JButton cmdStart = new JButton("Start");
scrlScriptTree.setBounds(4, 4, WIDTH / 2 - 4 - 64, HEIGHT - 4 - 28); cmdStart.setBounds(WIDTH - 96 - 4, HEIGHT - 24 - 4, 96, 24);
cmdStart.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
String s = getScriptName(tree.getSelectionPath().toString());
if (s != null) {
try {
WebUtil.getContents("http://bdn.parabot.org/api/v2/scripts/local", "script=" + URLEncoder.encode(s, "UTF-8") + "&username=" + URLEncoder.encode(Context.getUsername(), "UTF-8"));
} catch (MalformedURLException | UnsupportedEncodingException e1) {
e1.printStackTrace();
}
runScript(format.get(s));
}
}
});
JScrollPane scrlScriptInfo = new JScrollPane(scriptInfo); JButton cmdHome = new JButton("Open home");
scrlScriptInfo.setBounds(WIDTH / 2 + 4 - 64, 4, WIDTH / 2 - 8 + 64, cmdHome.setBounds(WIDTH - (96 * 2) - 4 - 32, HEIGHT - 24 - 4, 96 + 32,
HEIGHT - 4 - 28); 24);
cmdHome.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
try {
Desktop.getDesktop().open(Directories.getWorkspace());
} catch (Exception ex) {
ex.printStackTrace();
}
}
});
JButton cmdStart = new JButton("Start"); panel.add(scrlScriptTree);
cmdStart.setBounds(WIDTH - 96 - 4, HEIGHT - 24 - 4, 96, 24); panel.add(scrlScriptInfo);
cmdStart.addActionListener(new ActionListener() { panel.add(cmdStart);
@Override panel.add(cmdHome);
public void actionPerformed(ActionEvent e) {
String s = getScriptName(tree.getSelectionPath().toString());
if (s != null) {
try {
WebUtil.getContents("http://bdn.parabot.org/api/v2/scripts/local", "script=" + URLEncoder.encode(s, "UTF-8") + "&username=" + URLEncoder.encode(Context.getUsername(), "UTF-8"));
} catch (MalformedURLException | UnsupportedEncodingException e1) {
e1.printStackTrace();
}
runScript(format.get(s));
}
}
});
JButton cmdHome = new JButton("Open home"); this.add(panel);
cmdHome.setBounds(WIDTH - (96 * 2) - 4 - 32, HEIGHT - 24 - 4, 96 + 32, this.pack();
24); this.setLocationRelativeTo(getOwner());
cmdHome.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
try {
Desktop.getDesktop().open(Directories.getWorkspace());
} catch (Exception ex) {
ex.printStackTrace();
}
}
});
panel.add(scrlScriptTree); }
panel.add(scrlScriptInfo);
panel.add(cmdStart);
panel.add(cmdHome);
this.add(panel); private class ScriptTreeCellRenderer implements TreeCellRenderer {
this.pack(); private JLabel label;
this.setLocationRelativeTo(getOwner());
} ScriptTreeCellRenderer() {
label = new JLabel();
}
private class ScriptTreeCellRenderer implements TreeCellRenderer { @Override
private JLabel label; public Component getTreeCellRendererComponent(JTree list, Object value,
boolean selected, boolean expanded, boolean leaf, int row,
ScriptTreeCellRenderer() { boolean focused) {
label = new JLabel(); Object o = ((DefaultMutableTreeNode) value).getUserObject();
} BufferedImage icon = (o instanceof Category ? ((Category) o)
.getIcon() : Category.getIcon("script"));
@Override label.setIcon(icon != null ? new ImageIcon(icon) : null);
public Component getTreeCellRendererComponent(JTree list, Object value, label.setFont(o instanceof Category ? fontCategory : fontScript);
boolean selected, boolean expanded, boolean leaf, int row, label.setForeground(selected ? Color.DARK_GRAY : Color.BLACK);
boolean focused) { label.setText(String.valueOf(value));
Object o = ((DefaultMutableTreeNode) value).getUserObject(); return label;
BufferedImage icon = (o instanceof Category ? ((Category) o) }
.getIcon() : Category.getIcon("script")); }
label.setIcon(icon != null ? new ImageIcon(icon) : null);
label.setFont(o instanceof Category ? fontCategory : fontScript);
label.setForeground(selected ? Color.DARK_GRAY : Color.BLACK);
label.setText(String.valueOf(value));
return label;
}
}
private Font fontCategory = new Font("Arial", Font.BOLD, 12);
private Font fontScript = new Font("Arial", Font.PLAIN, 12);
private JTree tree;
private JEditorPane scriptInfo;
} }
@@ -11,97 +11,94 @@ import java.util.LinkedList;
import java.util.Queue; import java.util.Queue;
/** /**
*
* Shows a list of every supported server which can be started * Shows a list of every supported server which can be started
* *
* @author Dane, Everel * @author Dane, Everel
*
*/ */
public class ServerSelector extends JPanel { public class ServerSelector extends JPanel {
public static String initServer; private static final long serialVersionUID = 5238720307271493899L;
private static final long serialVersionUID = 5238720307271493899L; public static String initServer;
private static ServerSelector instance; private static ServerSelector instance;
public static ServerSelector getInstance() { public ServerSelector() {
if (instance == null) { Queue<ServerComponent> widgets = getServers();
instance = new ServerSelector(); if (initServer != null) {
} if (runServer(widgets)) {
return instance; initServer = null;
} return;
}
}
public ServerSelector() { setLayout(new BorderLayout());
Queue<ServerComponent> widgets = getServers(); setPreferredSize(new Dimension(600, 350));
if (initServer != null) {
if (runServer(widgets)) {
initServer = null;
return;
}
}
JPanel interior = new JPanel(null);
setLayout(new BorderLayout()); int i = 0;
setPreferredSize(new Dimension(600, 350)); int y = 0;
while (widgets != null && !widgets.isEmpty()) {
final ServerComponent w = widgets.poll();
w.setSize(300, 100);
if (i % 2 == 0 && i != 0) {
y += 100;
}
w.setLocation(i % 2 == 0 ? 0 : 300, y);
interior.add(w);
i++;
}
y += 100;
interior.setPreferredSize(new Dimension(300, y));
JPanel interior = new JPanel(null); JScrollPane scrlInterior = new JScrollPane(interior);
scrlInterior
.setHorizontalScrollBarPolicy(JScrollPane.HORIZONTAL_SCROLLBAR_NEVER);
scrlInterior
.setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS);
add(scrlInterior);
int i = 0; }
int y = 0;
while (widgets != null && !widgets.isEmpty()) {
final ServerComponent w = widgets.poll();
w.setSize(300, 100);
if(i % 2 == 0 && i != 0) {
y += 100;
}
w.setLocation(i % 2 == 0 ? 0 : 300, y);
interior.add(w);
i++;
}
y += 100;
interior.setPreferredSize(new Dimension(300, y));
JScrollPane scrlInterior = new JScrollPane(interior); public static ServerSelector getInstance() {
scrlInterior if (instance == null) {
.setHorizontalScrollBarPolicy(JScrollPane.HORIZONTAL_SCROLLBAR_NEVER); instance = new ServerSelector();
scrlInterior }
.setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS); return instance;
add(scrlInterior); }
} /**
* This method is called when -server argument is given
*
* @param widgets
*/
private boolean runServer(Queue<ServerComponent> widgets) {
if (widgets == null || widgets.isEmpty()) {
return false;
}
final String serverName = initServer.toLowerCase();
for (ServerComponent widget : widgets) {
if (widget.desc.getServerName().toLowerCase().equals(serverName)) {
Environment.load(widget.desc);
return true;
}
}
return false;
}
/** /**
* This method is called when -server argument is given * Fetches array of server widgets
* *
* @param widgets * @return widgets array
*/ */
private boolean runServer(Queue<ServerComponent> widgets) { public Queue<ServerComponent> getServers() {
if (widgets == null || widgets.isEmpty()) { final Queue<ServerComponent> widgets = new LinkedList<>();
return false; ServerDescription[] servers = ServerParser.getDescriptions();
} if (servers != null) {
final String serverName = initServer.toLowerCase(); for (ServerDescription desc : servers) {
for (ServerComponent widget : widgets) { widgets.add(new ServerComponent(desc));
if (widget.desc.getServerName().toLowerCase().equals(serverName)) { }
Environment.load(widget.desc); }
return true; return widgets;
} }
}
return false;
}
/**
* Fetches array of server widgets
*
* @return widgets array
*/
public Queue<ServerComponent> getServers() {
final Queue<ServerComponent> widgets = new LinkedList<>();
ServerDescription[] servers = ServerParser.getDescriptions();
if (servers != null) {
for (ServerDescription desc : servers) {
widgets.add(new ServerComponent(desc));
}
}
return widgets;
}
} }
@@ -6,52 +6,50 @@ import javax.swing.*;
import java.awt.*; import java.awt.*;
/** /**
*
* Main panel where applets are added. * Main panel where applets are added.
* *
* @author Everel * @author Everel
*
*/ */
public class GamePanel extends JPanel { public class GamePanel extends JPanel {
private static final long serialVersionUID = 1L; private static final long serialVersionUID = 1L;
private static GamePanel instance; private static GamePanel instance;
private GamePanel() { private GamePanel() {
setFocusable(true); setFocusable(true);
setFocusTraversalKeysEnabled(false); setFocusTraversalKeysEnabled(false);
setOpaque(true); setOpaque(true);
setBackground(Color.black); setBackground(Color.black);
setPreferredSize(new Dimension(770, 503)); setPreferredSize(new Dimension(770, 503));
GroupLayout panelLayout = new GroupLayout(this); GroupLayout panelLayout = new GroupLayout(this);
setLayout(panelLayout); setLayout(panelLayout);
panelLayout.setHorizontalGroup(panelLayout.createParallelGroup( panelLayout.setHorizontalGroup(panelLayout.createParallelGroup(
GroupLayout.Alignment.LEADING).addGap(0, 770, Short.MAX_VALUE)); GroupLayout.Alignment.LEADING).addGap(0, 770, Short.MAX_VALUE));
panelLayout.setVerticalGroup(panelLayout.createParallelGroup( panelLayout.setVerticalGroup(panelLayout.createParallelGroup(
GroupLayout.Alignment.LEADING).addGap(0, 418, Short.MAX_VALUE)); GroupLayout.Alignment.LEADING).addGap(0, 418, Short.MAX_VALUE));
} }
/** /**
* Updates context of this panel and adds a different Applet to the panel * Gets instance of this panel
* *
* @param c * @return instance of this panel
*/ */
public void setContext(final Context c) { public static GamePanel getInstance() {
add(c.getApplet(), BorderLayout.CENTER); return instance == null ? instance = new GamePanel() : instance;
} }
/** /**
* Gets instance of this panel * Updates context of this panel and adds a different Applet to the panel
* *
* @return instance of this panel * @param c
*/ */
public static GamePanel getInstance() { public void setContext(final Context c) {
return instance == null ? instance = new GamePanel() : instance; add(c.getApplet(), BorderLayout.CENTER);
} }
/** /**
* Removes all components * Removes all components
*/ */
public void removeComponents() { public void removeComponents() {
removeAll(); removeAll();
} }
} }
@@ -1,90 +1,84 @@
package org.parabot.core.ui.components; package org.parabot.core.ui.components;
import java.awt.AlphaComposite;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.image.BufferedImage;
import javax.swing.JComponent;
import org.parabot.core.Context; import org.parabot.core.Context;
import org.parabot.environment.api.interfaces.Paintable; import org.parabot.environment.api.interfaces.Paintable;
import org.parabot.environment.api.utils.Time; import org.parabot.environment.api.utils.Time;
import javax.swing.*;
import java.awt.*;
import java.awt.image.BufferedImage;
/** /**
*
* The panel that is painted on * The panel that is painted on
* *
* @author Everel * @author Everel
*
*/ */
public class PaintComponent extends JComponent implements Runnable { public class PaintComponent extends JComponent implements Runnable {
private static final long serialVersionUID = 4653612412080038193L; private static final long serialVersionUID = 4653612412080038193L;
private static PaintComponent instance; private static PaintComponent instance;
private BufferedImage buffer; private BufferedImage buffer;
private Graphics2D g2; private Graphics2D g2;
private Dimension dimensions; private Dimension dimensions;
private Context context; private Context context;
private PaintComponent(Dimension dimensions) { private PaintComponent(Dimension dimensions) {
this.dimensions = dimensions; this.dimensions = dimensions;
this.buffer = new BufferedImage(dimensions.width, dimensions.height, BufferedImage.TYPE_INT_ARGB); this.buffer = new BufferedImage(dimensions.width, dimensions.height, BufferedImage.TYPE_INT_ARGB);
this.g2 = buffer.createGraphics(); this.g2 = buffer.createGraphics();
setPreferredSize(dimensions); setPreferredSize(dimensions);
setSize(dimensions); setSize(dimensions);
setOpaque(false); setOpaque(false);
setIgnoreRepaint(true); setIgnoreRepaint(true);
} }
public void setDimensions(Dimension dimensions) { public static PaintComponent getInstance(Dimension dimensions) {
this.dimensions = dimensions; return instance == null ? instance = new PaintComponent(dimensions) : instance;
this.dimensions = dimensions; }
this.buffer = new BufferedImage(dimensions.width, dimensions.height, BufferedImage.TYPE_INT_ARGB);
this.g2 = buffer.createGraphics();
setPreferredSize(dimensions); public static PaintComponent getInstance() {
setSize(dimensions); return getInstance(null);
setOpaque(false); }
setIgnoreRepaint(true);
}
public static PaintComponent getInstance(Dimension dimensions) { public void setDimensions(Dimension dimensions) {
return instance == null ? instance = new PaintComponent(dimensions) : instance; this.dimensions = dimensions;
} this.dimensions = dimensions;
this.buffer = new BufferedImage(dimensions.width, dimensions.height, BufferedImage.TYPE_INT_ARGB);
this.g2 = buffer.createGraphics();
public static PaintComponent getInstance() { setPreferredSize(dimensions);
return getInstance(null); setSize(dimensions);
} setOpaque(false);
setIgnoreRepaint(true);
}
public void startPainting(Context context) { public void startPainting(Context context) {
this.context = context; this.context = context;
new Thread(this).start(); new Thread(this).start();
} }
@Override @Override
public void paintComponent(Graphics g) { public void paintComponent(Graphics g) {
g2.setComposite(AlphaComposite.Clear); g2.setComposite(AlphaComposite.Clear);
g2.fillRect(0, 0, dimensions.width, dimensions.height); g2.fillRect(0, 0, dimensions.width, dimensions.height);
g2.setComposite(AlphaComposite.SrcOver); g2.setComposite(AlphaComposite.SrcOver);
if(context != null) { if (context != null) {
for(Paintable p : context.getPaintables()) { for (Paintable p : context.getPaintables()) {
p.paint(g); p.paint(g);
} }
context.getPaintDebugger().debug(g2); context.getPaintDebugger().debug(g2);
} }
g.drawImage(buffer, 0, 0, null); g.drawImage(buffer, 0, 0, null);
} }
@Override @Override
public void run() { public void run() {
while(true) { while (true) {
Time.sleep(100); Time.sleep(100);
repaint(); repaint();
} }
} }
} }
@@ -1,53 +1,51 @@
package org.parabot.core.ui.components; package org.parabot.core.ui.components;
import java.awt.Color; import java.awt.*;
import java.awt.FontMetrics;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.RenderingHints;
import java.awt.geom.Rectangle2D; import java.awt.geom.Rectangle2D;
/** /**
*
* ProgressBar * ProgressBar
* *
* @author Everel * @author Everel
*
*/ */
public class ProgressBar { public class ProgressBar {
private double value; private double value;
private int width; private int width;
private int height; private int height;
private double locX; private double locX;
private Color progColor; private Color progColor;
private Color backColor; private Color backColor;
private FontMetrics fontMetrics; private FontMetrics fontMetrics;
private String text; private String text;
public ProgressBar(int width, int height) { public ProgressBar(int width, int height) {
this.progColor = new Color(255, 0, 0); this.progColor = new Color(255, 0, 0);
this.backColor = new Color(74, 74, 72, 100); this.backColor = new Color(74, 74, 72, 100);
this.width = width; this.width = width;
this.height = height; this.height = height;
this.text = ""; this.text = "";
} }
public void setText(final String text) { public void setText(final String text) {
this.text = text; this.text = text;
} }
public void setValue(double value) { public double getValue() {
if(value < 0 || value > 100) { return value;
return; }
}
if(value > 99) {
value = 100;
}
this.value = value;
this.locX = (width / 100.0D) * value;
int val = (int) value; public void setValue(double value) {
/*if (value <= 50) { if (value < 0 || value > 100) {
return;
}
if (value > 99) {
value = 100;
}
this.value = value;
this.locX = (width / 100.0D) * value;
int val = (int) value;
/*if (value <= 50) {
this.progColor = new Color(255, (2 * val), 0); this.progColor = new Color(255, (2 * val), 0);
} else { } else {
val -= 50; val -= 50;
@@ -55,38 +53,34 @@ public class ProgressBar {
100 + (2 * val), 0); 100 + (2 * val), 0);
}*/ }*/
int r = (int) (((double) (225 - 218) * (double) val) / ((double) 100.D)); int r = (int) (((double) (225 - 218) * (double) val) / ((double) 100.D));
int g = (int) (((double) (253 - 165) * (double) val) / ((double) 100.D)); int g = (int) (((double) (253 - 165) * (double) val) / ((double) 100.D));
int b = (int) (((double) (145 - 32) * (double) val) / ((double) 100.D)); int b = (int) (((double) (145 - 32) * (double) val) / ((double) 100.D));
this.progColor = new Color(255 - r, 253 - g, 145 - b); this.progColor = new Color(255 - r, 253 - g, 145 - b);
} }
public double getValue() { public void draw(Graphics g, int x, int y) {
return value; Graphics2D g2 = (Graphics2D) g;
} g2.setRenderingHint(
RenderingHints.KEY_TEXT_ANTIALIASING,
RenderingHints.VALUE_TEXT_ANTIALIAS_ON);
if (fontMetrics == null) {
fontMetrics = g2.getFontMetrics();
}
g2.setColor(backColor);
g2.fillRect(x, y, width, height);
g2.setColor(Color.DARK_GRAY);
g2.drawRect(x - 1, y - 1, width + 1, height + 1);
g2.setColor(this.progColor);
g2.fill(new Rectangle2D.Double(x, y, locX, height));
public void draw(Graphics g, int x, int y) { int value = (int) getValue();
Graphics2D g2 = (Graphics2D) g; String percent = Integer.toString(value) + "% " + text;
g2.setRenderingHint(
RenderingHints.KEY_TEXT_ANTIALIASING,
RenderingHints.VALUE_TEXT_ANTIALIAS_ON);
if (fontMetrics == null) {
fontMetrics = g2.getFontMetrics();
}
g2.setColor(backColor);
g2.fillRect(x, y, width, height);
g2.setColor(Color.DARK_GRAY);
g2.drawRect(x - 1, y - 1, width + 1, height + 1);
g2.setColor(this.progColor);
g2.fill(new Rectangle2D.Double(x, y, locX, height));
int value = (int) getValue(); int strX = (x + (width / 2)) - (fontMetrics.stringWidth(percent) / 2);
String percent = Integer.toString(value) + "% " + text; g2.setColor(Color.white);
g2.drawString(percent, strX, y + 13);
int strX = (x + (width / 2)) - (fontMetrics.stringWidth(percent) / 2); }
g2.setColor(Color.white);
g2.drawString(percent, strX, y + 13);
}
} }
@@ -1,131 +1,124 @@
package org.parabot.core.ui.components; package org.parabot.core.ui.components;
import java.awt.Color;
import java.awt.Cursor;
import java.awt.Font;
import java.awt.FontMetrics;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.event.MouseMotionListener;
import javax.swing.JPanel;
import org.parabot.core.desc.ServerDescription; import org.parabot.core.desc.ServerDescription;
import org.parabot.core.ui.fonts.Fonts; import org.parabot.core.ui.fonts.Fonts;
import org.parabot.environment.Environment; import org.parabot.environment.Environment;
import javax.swing.*;
import java.awt.*;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.event.MouseMotionListener;
/** /**
* A neat looking server component * A neat looking server component
* *
* @author Everel * @author Everel
*
*/ */
public class ServerComponent extends JPanel implements MouseListener, public class ServerComponent extends JPanel implements MouseListener,
MouseMotionListener { MouseMotionListener {
private static final long serialVersionUID = 1L; private static final long serialVersionUID = 1L;
public ServerDescription desc; public ServerDescription desc;
private String name; private String name;
private boolean hovered; private boolean hovered;
public ServerComponent(final ServerDescription desc) { public ServerComponent(final ServerDescription desc) {
this.desc = desc; this.desc = desc;
setLayout(null); setLayout(null);
this.name = desc.getServerName().replaceAll(" ", ""); this.name = desc.getServerName().replaceAll(" ", "");
addMouseListener(this); addMouseListener(this);
addMouseMotionListener(this); addMouseMotionListener(this);
setCursor(Cursor.getPredefinedCursor(Cursor.HAND_CURSOR)); setCursor(Cursor.getPredefinedCursor(Cursor.HAND_CURSOR));
} }
@Override @Override
public String getName() { public String getName() {
return name; return name;
} }
@Override @Override
public void paintComponent(Graphics g) { public void paintComponent(Graphics g) {
Graphics2D g2d = (Graphics2D) g; Graphics2D g2d = (Graphics2D) g;
setOpaque(false); setOpaque(false);
super.paintComponent(g); super.paintComponent(g);
setOpaque(true); setOpaque(true);
int w = getWidth(); int w = getWidth();
int h = getHeight(); int h = getHeight();
Color bgColor = Color.LIGHT_GRAY; Color bgColor = Color.LIGHT_GRAY;
if (hovered) { if (hovered) {
bgColor = Color.GRAY; bgColor = Color.GRAY;
} }
g2d.setColor(bgColor); g2d.setColor(bgColor);
g2d.fillRect(0, 0, w, h); g2d.fillRect(0, 0, w, h);
g.setColor(Color.black); g.setColor(Color.black);
Font title = Fonts.getResource("leelawadee.ttf", 16); Font title = Fonts.getResource("leelawadee.ttf", 16);
g.setFont(title); g.setFont(title);
String serverName = desc.getServerName(); String serverName = desc.getServerName();
int sw = g.getFontMetrics().stringWidth(serverName); int sw = g.getFontMetrics().stringWidth(serverName);
g.drawString(serverName, (w / 2) - (sw / 2), 30); g.drawString(serverName, (w / 2) - (sw / 2), 30);
Font normal = Fonts.getResource("leelawadee.ttf"); Font normal = Fonts.getResource("leelawadee.ttf");
g.setFont(normal); g.setFont(normal);
FontMetrics fm = g.getFontMetrics(); FontMetrics fm = g.getFontMetrics();
String author = "Author: " + desc.getAuthor(); String author = "Author: " + desc.getAuthor();
String revision = "Revision: " + desc.getRevision(); String revision = "Revision: " + desc.getRevision();
g.drawString(author, (w / 2) - (fm.stringWidth(author) / 2), 55); g.drawString(author, (w / 2) - (fm.stringWidth(author) / 2), 55);
g.drawString(revision, (w / 2) - (fm.stringWidth(revision) / 2), 70); g.drawString(revision, (w / 2) - (fm.stringWidth(revision) / 2), 70);
} }
public void load(final ServerDescription desc) { public void load(final ServerDescription desc) {
VerboseLoader.get().switchState(VerboseLoader.STATE_LOADING); VerboseLoader.get().switchState(VerboseLoader.STATE_LOADING);
new Thread(new Runnable() { new Thread(new Runnable() {
@Override @Override
public void run() { public void run() {
Environment.load(desc); Environment.load(desc);
} }
}).start(); }).start();
} }
@Override @Override
public void mouseMoved(MouseEvent e) { public void mouseMoved(MouseEvent e) {
if (!hovered) { if (!hovered) {
hovered = true; hovered = true;
this.repaint(); this.repaint();
} }
} }
@Override @Override
public void mouseExited(MouseEvent e) { public void mouseExited(MouseEvent e) {
if (hovered) { if (hovered) {
hovered = false; hovered = false;
this.repaint(); this.repaint();
} }
} }
@Override @Override
public void mousePressed(MouseEvent e) { public void mousePressed(MouseEvent e) {
if (hovered) { if (hovered) {
load(desc); load(desc);
} }
} }
@Override @Override
public void mouseDragged(MouseEvent e) { public void mouseDragged(MouseEvent e) {
} }
@Override @Override
public void mouseClicked(MouseEvent e) { public void mouseClicked(MouseEvent e) {
} }
@Override @Override
public void mouseEntered(MouseEvent e) { public void mouseEntered(MouseEvent e) {
} }
@Override @Override
public void mouseReleased(MouseEvent e) { public void mouseReleased(MouseEvent e) {
} }
} }
@@ -6,8 +6,8 @@ import org.parabot.core.forum.AccountManager;
import org.parabot.core.forum.AccountManagerAccess; import org.parabot.core.forum.AccountManagerAccess;
import org.parabot.core.io.ProgressListener; import org.parabot.core.io.ProgressListener;
import org.parabot.core.ui.ServerSelector; import org.parabot.core.ui.ServerSelector;
import org.parabot.core.ui.images.Images;
import org.parabot.core.ui.fonts.Fonts; import org.parabot.core.ui.fonts.Fonts;
import org.parabot.core.ui.images.Images;
import org.parabot.core.ui.utils.UILog; import org.parabot.core.ui.utils.UILog;
import javax.swing.*; import javax.swing.*;
@@ -24,22 +24,13 @@ import java.awt.image.RescaleOp;
* @author Everel, EmmaStone * @author Everel, EmmaStone
*/ */
public class VerboseLoader extends JPanel implements ProgressListener { public class VerboseLoader extends JPanel implements ProgressListener {
public static final int STATE_LOADING = 1;
private static final long serialVersionUID = 7412412644921803896L; private static final long serialVersionUID = 7412412644921803896L;
private static final int STATE_AUTHENTICATION = 0;
private static final int STATE_SERVER_SELECT = 2;
private static VerboseLoader current; private static VerboseLoader current;
private static String state = "Initializing loader..."; private static String state = "Initializing loader...";
private static final int STATE_AUTHENTICATION = 0;
public static final int STATE_LOADING = 1;
private static final int STATE_SERVER_SELECT = 2;
private int currentState;
private static AccountManager manager; private static AccountManager manager;
private FontMetrics fontMetrics;
private BufferedImage background, banner, loginBox;
private ProgressBar progressBar;
private JPanel loginPanel;
public static final AccountManagerAccess MANAGER_FETCHER = new AccountManagerAccess() { public static final AccountManagerAccess MANAGER_FETCHER = new AccountManagerAccess() {
@Override @Override
@@ -48,6 +39,11 @@ public class VerboseLoader extends JPanel implements ProgressListener {
} }
}; };
private int currentState;
private FontMetrics fontMetrics;
private BufferedImage background, banner, loginBox;
private ProgressBar progressBar;
private JPanel loginPanel;
private VerboseLoader(String username, String password) { private VerboseLoader(String username, String password) {
if (current != null) { if (current != null) {
@@ -77,10 +73,38 @@ public class VerboseLoader extends JPanel implements ProgressListener {
} }
} }
/**
* Gets instance of this panel
*
* @return instance of this panel
*/
public static VerboseLoader get(String username, String password) {
return current == null ? new VerboseLoader(username, password) : current;
}
/**
* Gets instance of this panel
*
* @return instance of this panel
*/
public static VerboseLoader get() {
return current == null ? new VerboseLoader(null, null) : current;
}
/**
* Updates the status message and repaints the panel
*
* @param message
*/
public static void setState(final String message) {
state = message;
current.repaint();
}
public void addServerPanel() { public void addServerPanel() {
JPanel servers = ServerSelector.getInstance(); JPanel servers = ServerSelector.getInstance();
GridBagLayout bagLayout = (GridBagLayout) getLayout(); GridBagLayout bagLayout = (GridBagLayout) getLayout();
GridBagConstraints c = new GridBagConstraints(); GridBagConstraints c = new GridBagConstraints();
c.weightx = 1; c.weightx = 1;
c.weighty = 1; c.weighty = 1;
@@ -139,7 +163,6 @@ public class VerboseLoader extends JPanel implements ProgressListener {
passwordLabel.setAlignmentX(Box.CENTER_ALIGNMENT); passwordLabel.setAlignmentX(Box.CENTER_ALIGNMENT);
passwordLabel.setForeground(Color.white); passwordLabel.setForeground(Color.white);
login.setAlignmentX(Box.CENTER_ALIGNMENT); login.setAlignmentX(Box.CENTER_ALIGNMENT);
login.setOpaque(false); login.setOpaque(false);
@@ -189,16 +212,15 @@ public class VerboseLoader extends JPanel implements ProgressListener {
public void paintComponent(Graphics graphics) { public void paintComponent(Graphics graphics) {
super.paintComponent(graphics); super.paintComponent(graphics);
Graphics2D g = (Graphics2D) graphics; Graphics2D g = (Graphics2D) graphics;
g.setRenderingHint( g.setRenderingHint(
RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.KEY_TEXT_ANTIALIASING,
RenderingHints.VALUE_TEXT_ANTIALIAS_ON); RenderingHints.VALUE_TEXT_ANTIALIAS_ON);
g.drawImage(background, 0, 0, null); g.drawImage(background, 0, 0, null);
float[] scales = {1f, 1f, 1f, 0.9f}; float[] scales = { 1f, 1f, 1f, 0.9f };
float[] offsets = new float[4]; float[] offsets = new float[4];
RescaleOp rop = new RescaleOp(scales, offsets, null); RescaleOp rop = new RescaleOp(scales, offsets, null);
g.drawImage(banner, rop, 0, 0); g.drawImage(banner, rop, 0, 0);
g.setStroke(new BasicStroke(5)); g.setStroke(new BasicStroke(5));
@@ -236,7 +258,6 @@ public class VerboseLoader extends JPanel implements ProgressListener {
g.drawString(state, x, 200); g.drawString(state, x, 200);
} }
g.setFont(Fonts.getResource("leelawadee.ttf")); g.setFont(Fonts.getResource("leelawadee.ttf"));
final String version = Configuration.BOT_VERSION.get(); final String version = Configuration.BOT_VERSION.get();
g.drawString(version, g.drawString(version,
@@ -244,35 +265,6 @@ public class VerboseLoader extends JPanel implements ProgressListener {
getHeight() - 12); getHeight() - 12);
} }
/**
* Gets instance of this panel
*
* @return instance of this panel
*/
public static VerboseLoader get(String username, String password) {
return current == null ? new VerboseLoader(username, password) : current;
}
/**
* Gets instance of this panel
*
* @return instance of this panel
*/
public static VerboseLoader get() {
return current == null ? new VerboseLoader(null, null) : current;
}
/**
* Updates the status message and repaints the panel
*
* @param message
*/
public static void setState(final String message) {
state = message;
current.repaint();
}
@Override @Override
public void onProgressUpdate(double value) { public void onProgressUpdate(double value) {
progressBar.setValue(value); progressBar.setValue(value);
@@ -1,86 +1,87 @@
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<?import javafx.scene.control.*?> <?import javafx.scene.control.*?>
<?import java.lang.*?>
<?import javafx.scene.layout.*?> <?import javafx.scene.layout.*?>
<BorderPane xmlns:fx="http://javafx.com/fxml/1" maxHeight="-Infinity" maxWidth="-Infinity" minHeight="500.0" minWidth="500.0"
prefHeight="503.0" prefWidth="735.0" xmlns="http://javafx.com/javafx/8">
<BorderPane maxHeight="-Infinity" maxWidth="-Infinity" minHeight="500.0" minWidth="500.0" prefHeight="503.0" prefWidth="735.0" xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1"> <top>
<top> <MenuBar BorderPane.alignment="CENTER">
<MenuBar BorderPane.alignment="CENTER"> <menus>
<menus> <Menu mnemonicParsing="false" text="File">
<Menu mnemonicParsing="false" text="File"> <items>
<items> <MenuItem mnemonicParsing="false" text="Close"/>
<MenuItem mnemonicParsing="false" text="Close" /> </items>
</items> </Menu>
</Menu> <Menu mnemonicParsing="false" text="Edit">
<Menu mnemonicParsing="false" text="Edit"> <items>
<items> <MenuItem mnemonicParsing="false" text="Delete"/>
<MenuItem mnemonicParsing="false" text="Delete" /> </items>
</items> </Menu>
</Menu> <Menu mnemonicParsing="false" text="Help">
<Menu mnemonicParsing="false" text="Help"> <items>
<items> <MenuItem mnemonicParsing="false" text="About"/>
<MenuItem mnemonicParsing="false" text="About" /> </items>
</items> </Menu>
</Menu> </menus>
</menus> </MenuBar>
</MenuBar> </top>
</top> <center>
<center> <TabPane>
<TabPane> <tabs>
<tabs> <Tab closable="false" text="Scripts">
<Tab closable="false" text="Scripts"> <content>
<content> <BorderPane prefHeight="200.0" prefWidth="200.0" BorderPane.alignment="CENTER">
<BorderPane prefHeight="200.0" prefWidth="200.0" BorderPane.alignment="CENTER"> <top>
<top> <ToolBar prefHeight="40.0" prefWidth="200.0" BorderPane.alignment="CENTER">
<ToolBar prefHeight="40.0" prefWidth="200.0" BorderPane.alignment="CENTER"> <items>
<items> <TextField promptText="Search query"/>
<TextField promptText="Search query" /> <Separator prefHeight="30.0" prefWidth="25.0" visible="false"/>
<Separator prefHeight="30.0" prefWidth="25.0" visible="false" /> <ComboBox prefWidth="150.0" promptText="Category"/>
<ComboBox prefWidth="150.0" promptText="Category" /> <Separator prefHeight="30.0" prefWidth="25.0" visible="false"/>
<Separator prefHeight="30.0" prefWidth="25.0" visible="false" /> <CheckBox mnemonicParsing="false" text="All servers"/>
<CheckBox mnemonicParsing="false" text="All servers" /> <Separator prefHeight="30.0" prefWidth="25.0" visible="false"/>
<Separator prefHeight="30.0" prefWidth="25.0" visible="false" /> <CheckBox mnemonicParsing="false" text="Include local scripts"/>
<CheckBox mnemonicParsing="false" text="Include local scripts" /> <Separator prefHeight="30.0" prefWidth="25.0" visible="false"/>
<Separator prefHeight="30.0" prefWidth="25.0" visible="false" /> <Button alignment="CENTER_RIGHT" mnemonicParsing="false" text="Search"/>
<Button alignment="CENTER_RIGHT" mnemonicParsing="false" text="Search" /> </items>
</items> </ToolBar>
</ToolBar> </top>
</top> <center>
<center> <TableView prefHeight="200.0" prefWidth="200.0" BorderPane.alignment="CENTER">
<TableView prefHeight="200.0" prefWidth="200.0" BorderPane.alignment="CENTER"> <columns>
<columns> <TableColumn prefWidth="75.0" text="Name"/>
<TableColumn prefWidth="75.0" text="Name" /> <TableColumn prefWidth="75.0" text="Category"/>
<TableColumn prefWidth="75.0" text="Category" /> <TableColumn prefWidth="75.0" text="Price"/>
<TableColumn prefWidth="75.0" text="Price" /> </columns>
</columns> <contextMenu>
<contextMenu> <ContextMenu>
<ContextMenu> <items>
<items> <MenuItem mnemonicParsing="false" text="View information"/>
<MenuItem mnemonicParsing="false" text="View information" /> </items>
</items> </ContextMenu>
</ContextMenu> </contextMenu>
</contextMenu> </TableView>
</TableView> </center>
</center> <bottom>
<bottom> <HBox alignment="CENTER_RIGHT" prefHeight="35.0" prefWidth="735.0"
<HBox alignment="CENTER_RIGHT" prefHeight="35.0" prefWidth="735.0" BorderPane.alignment="CENTER"> BorderPane.alignment="CENTER">
<children> <children>
<Button mnemonicParsing="false" prefHeight="25.0" prefWidth="83.0" text="Start" /> <Button mnemonicParsing="false" prefHeight="25.0" prefWidth="83.0"
<Separator prefHeight="4.0" prefWidth="35.0" visible="false" /> text="Start"/>
</children> <Separator prefHeight="4.0" prefWidth="35.0" visible="false"/>
</HBox> </children>
</bottom> </HBox>
</BorderPane> </bottom>
</content> </BorderPane>
</Tab> </content>
<Tab text="JKChicken"> </Tab>
<content> <Tab text="JKChicken">
<BorderPane prefHeight="200.0" prefWidth="200.0" /> <content>
</content> <BorderPane prefHeight="200.0" prefWidth="200.0"/>
</Tab> </content>
</tabs> </Tab>
</TabPane> </tabs>
</center> </TabPane>
</center>
</BorderPane> </BorderPane>
@@ -13,6 +13,7 @@ public class Fonts {
* Calls the getResource with the default size of 12 * Calls the getResource with the default size of 12
* *
* @param resource * @param resource
*
* @return * @return
*/ */
public static Font getResource(final String resource) { public static Font getResource(final String resource) {
@@ -9,7 +9,7 @@ import java.io.IOException;
public class ParabotFont { public class ParabotFont {
private String location; private String location;
private Font font; private Font font;
public ParabotFont(String location, float size) { public ParabotFont(String location, float size) {
if (!location.toLowerCase().startsWith("/storage/fonts/")) { if (!location.toLowerCase().startsWith("/storage/fonts/")) {
@@ -2,7 +2,6 @@ package org.parabot.core.ui.listeners;
import org.parabot.core.ui.listeners.key.ActionEventBinding; import org.parabot.core.ui.listeners.key.ActionEventBinding;
import org.parabot.core.ui.listeners.key.Binding; import org.parabot.core.ui.listeners.key.Binding;
import org.parabot.environment.OperatingSystem;
import java.awt.event.KeyEvent; import java.awt.event.KeyEvent;
import java.awt.event.KeyListener; import java.awt.event.KeyListener;
@@ -31,15 +30,15 @@ public class PBKeyListener implements KeyListener {
} }
public void addBinding(Binding binding) { public void addBinding(Binding binding) {
for (Binding bind : this.bindings){ for (Binding bind : this.bindings) {
if (bind.getKey() == binding.getKey()){ if (bind.getKey() == binding.getKey()) {
return; return;
} }
} }
this.bindings.add(binding); this.bindings.add(binding);
} }
public void resetBindings(){ public void resetBindings() {
this.bindings = new ArrayList<>(); this.bindings = new ArrayList<>();
this.fillBindings(); this.fillBindings();
} }
@@ -10,7 +10,6 @@ import org.parabot.environment.api.utils.WebUtil;
import java.util.LinkedList; import java.util.LinkedList;
/** /**
* Initializes the bot environment * Initializes the bot environment
* *
@@ -1,25 +1,26 @@
package org.parabot.environment; package org.parabot.environment;
/** /**
*
* This class is used for detecting the user's operating system * This class is used for detecting the user's operating system
* *
* @author Everel * @author Everel
*
*/ */
public enum OperatingSystem { public enum OperatingSystem {
WINDOWS, LINUX, MAC, OTHER; WINDOWS, LINUX, MAC, OTHER;
public static final OperatingSystem getOS() { public static final OperatingSystem getOS() {
String str = System.getProperty("os.name").toLowerCase(); String str = System.getProperty("os.name").toLowerCase();
if (str.indexOf("win") > -1) if (str.indexOf("win") > -1) {
return OperatingSystem.WINDOWS; return OperatingSystem.WINDOWS;
if (str.indexOf("mac") > -1) }
return OperatingSystem.MAC; if (str.indexOf("mac") > -1) {
if (str.indexOf("nix") > -1 || str.indexOf("nux") > -1) return OperatingSystem.MAC;
return OperatingSystem.LINUX; }
return OperatingSystem.OTHER; if (str.indexOf("nix") > -1 || str.indexOf("nux") > -1) {
} return OperatingSystem.LINUX;
}
return OperatingSystem.OTHER;
}
} }
@@ -1,17 +1,15 @@
package org.parabot.environment.api.interfaces; package org.parabot.environment.api.interfaces;
import java.awt.Graphics; import java.awt.*;
/** /**
*
* @author Everel * @author Everel
*
*/ */
public interface Paintable { public interface Paintable {
/** /**
* @param g * @param g
*/ */
public void paint(Graphics g); public void paint(Graphics g);
} }
@@ -13,13 +13,13 @@ import java.security.NoSuchAlgorithmException;
*/ */
public class FileUtil { public class FileUtil {
public static String getChecksum(File file){ public static String getChecksum(File file) {
if (file.isFile()) { if (file.isFile()) {
try { try {
MessageDigest md = MessageDigest.getInstance("MD5"); MessageDigest md = MessageDigest.getInstance("MD5");
if (file.exists()) { if (file.exists()) {
FileInputStream fis = new FileInputStream(file); FileInputStream fis = new FileInputStream(file);
byte[] dataBytes = new byte[1024]; byte[] dataBytes = new byte[1024];
int nread; int nread;
@@ -49,8 +49,8 @@ public class FileUtil {
try { try {
MessageDigest md = MessageDigest.getInstance("MD5"); MessageDigest md = MessageDigest.getInstance("MD5");
if (file.exists()) { if (file.exists()) {
FileInputStream fis = new FileInputStream(file); FileInputStream fis = new FileInputStream(file);
byte[] dataBytes = new byte[1024]; byte[] dataBytes = new byte[1024];
int nread; int nread;
@@ -76,7 +76,7 @@ public class FileUtil {
if (!destFile.exists()) { if (!destFile.exists()) {
destFile.createNewFile(); destFile.createNewFile();
} }
FileChannel source = null; FileChannel source = null;
FileChannel destination = null; FileChannel destination = null;
source = new FileInputStream(sourceFile).getChannel(); source = new FileInputStream(sourceFile).getChannel();
destination = new FileOutputStream(destFile).getChannel(); destination = new FileOutputStream(destFile).getChannel();
@@ -3,15 +3,17 @@ package org.parabot.environment.api.utils;
/** /**
* A simple class to filter things out of an collection * A simple class to filter things out of an collection
* *
* @author Everel
*
* @param <F> * @param <F>
*
* @author Everel
*/ */
public interface Filter<F> { public interface Filter<F> {
/** /**
* Determines if this object should be accepted * Determines if this object should be accepted
* @param f *
* @return <b>true</b> to include this object, otherwise <b>false</b> to exclude. * @param f
*/ *
public boolean accept(F f); * @return <b>true</b> to include this object, otherwise <b>false</b> to exclude.
*/
public boolean accept(F f);
} }
@@ -6,10 +6,10 @@ package org.parabot.environment.api.utils;
public class JavaUtil { public class JavaUtil {
public static double JAVA_VERSION = getVersion(); public static double JAVA_VERSION = getVersion();
static double getVersion () { static double getVersion() {
String version = System.getProperty("java.version"); String version = System.getProperty("java.version");
int pos = version.indexOf('.'); int pos = version.indexOf('.');
pos = version.indexOf('.', pos+1); pos = version.indexOf('.', pos + 1);
return Double.parseDouble (version.substring (0, pos)); return Double.parseDouble(version.substring(0, pos));
} }
} }
@@ -3,44 +3,38 @@ package org.parabot.environment.api.utils;
import java.math.BigInteger; import java.math.BigInteger;
/** /**
*
* Helper class for calculating setters for clients that uses multipliers * Helper class for calculating setters for clients that uses multipliers
* *
* @author Everel * @author Everel
*
*/ */
public class Multipliers { public class Multipliers {
/** /**
* * @param multiplier the multiplier
* @param multiplier * @param set the value you want to set
* the multiplier *
* @param set * @return the correct setter value
* the value you want to set */
* @return the correct setter value public static int getIntSetter(int multiplier, int set) {
*/ int bits = 32;
public static int getIntSetter(int multiplier, int set) { BigInteger quotient = new BigInteger(Integer.toString(multiplier));
int bits = 32; BigInteger shift = BigInteger.ONE.shiftLeft(bits);
BigInteger quotient = new BigInteger(Integer.toString(multiplier)); int value = quotient.modInverse(shift).intValue();
BigInteger shift = BigInteger.ONE.shiftLeft(bits); return value * set;
int value = quotient.modInverse(shift).intValue(); }
return value * set;
}
/** /**
* * @param multiplier the multiplier
* @param multiplier * @param set the value you want to set
* the multiplier *
* @param set * @return the correct setter value
* the value you want to set */
* @return the correct setter value public static long getLongSetter(long multiplier, long set) {
*/ int bits = 64;
public static long getLongSetter(long multiplier, long set) { BigInteger quotient = new BigInteger(Long.toString(multiplier));
int bits = 64; BigInteger shift = BigInteger.ONE.shiftLeft(bits);
BigInteger quotient = new BigInteger(Long.toString(multiplier)); long value = quotient.modInverse(shift).longValue();
BigInteger shift = BigInteger.ONE.shiftLeft(bits); return value * set;
long value = quotient.modInverse(shift).longValue(); }
return value * set;
}
} }
@@ -19,16 +19,14 @@ import java.util.Properties;
public class PBPreferences { public class PBPreferences {
private static AccountManager manager; private static AccountManager manager;
private Properties properties;
private int scriptID;
public static final AccountManagerAccess MANAGER_FETCHER = new AccountManagerAccess() { public static final AccountManagerAccess MANAGER_FETCHER = new AccountManagerAccess() {
@Override @Override
public final void setManager(AccountManager manager) { public final void setManager(AccountManager manager) {
PBPreferences.manager = manager; PBPreferences.manager = manager;
} }
}; };
private Properties properties;
private int scriptID;
public PBPreferences(int scriptID) { public PBPreferences(int scriptID) {
this.scriptID = scriptID; this.scriptID = scriptID;
@@ -45,7 +43,7 @@ public class PBPreferences {
JSONArray resultArray; JSONArray resultArray;
if ((resultArray = ((JSONArray) result.get("result"))) != null) { if ((resultArray = ((JSONArray) result.get("result"))) != null) {
for(Object rObject : resultArray) { for (Object rObject : resultArray) {
JSONObject resultObject = (JSONObject) rObject; JSONObject resultObject = (JSONObject) rObject;
for (Object map : resultObject.entrySet()) { for (Object map : resultObject.entrySet()) {
Map.Entry<?, ?> pairs = (Map.Entry<?, ?>) map; Map.Entry<?, ?> pairs = (Map.Entry<?, ?>) map;
@@ -60,6 +58,7 @@ public class PBPreferences {
/** /**
* Change a setting * Change a setting
*
* @param key * @param key
* @param value * @param value
*/ */
@@ -69,27 +68,32 @@ public class PBPreferences {
/** /**
* Get a setting value * Get a setting value
*
* @param key * @param key
*
* @return * @return
*/ */
public Object getSetting(Object key){ public Object getSetting(Object key) {
return this.properties.get(key); return this.properties.get(key);
} }
/** /**
* Get a setting value as string * Get a setting value as string
*
* @param key * @param key
*
* @return * @return
*/ */
public String getSetting(String key){ public String getSetting(String key) {
return this.properties.getProperty(key); return this.properties.getProperty(key);
} }
/** /**
* Remove a setting * Remove a setting
*
* @param key * @param key
*/ */
public void removeSetting(Object key){ public void removeSetting(Object key) {
try { try {
JSONObject result = (JSONObject) WebUtil.getJsonParser().parse( JSONObject result = (JSONObject) WebUtil.getJsonParser().parse(
WebUtil.getContents("http://bdn.parabot.org/api/v2/user/preferences/set/", WebUtil.getContents("http://bdn.parabot.org/api/v2/user/preferences/set/",
@@ -98,7 +102,7 @@ public class PBPreferences {
"&script=" + String.valueOf(scriptID) "&script=" + String.valueOf(scriptID)
) )
); );
if ((boolean)result.get("result")){ if ((boolean) result.get("result")) {
this.properties.remove(key); this.properties.remove(key);
} }
} catch (ParseException | MalformedURLException | UnsupportedEncodingException e) { } catch (ParseException | MalformedURLException | UnsupportedEncodingException e) {
@@ -108,10 +112,11 @@ public class PBPreferences {
/** /**
* Add a setting * Add a setting
*
* @param key * @param key
* @param value * @param value
*/ */
public void addSetting(Object key, Object value){ public void addSetting(Object key, Object value) {
try { try {
JSONObject result = (JSONObject) WebUtil.getJsonParser().parse( JSONObject result = (JSONObject) WebUtil.getJsonParser().parse(
WebUtil.getContents("http://bdn.parabot.org/api/v2/user/preferences/set/", WebUtil.getContents("http://bdn.parabot.org/api/v2/user/preferences/set/",
@@ -121,7 +126,7 @@ public class PBPreferences {
"&script=" + String.valueOf(scriptID) "&script=" + String.valueOf(scriptID)
) )
); );
if ((boolean)result.get("result")){ if ((boolean) result.get("result")) {
this.properties.put(key, value); this.properties.put(key, value);
} }
} catch (ParseException | MalformedURLException | UnsupportedEncodingException e) { } catch (ParseException | MalformedURLException | UnsupportedEncodingException e) {
@@ -1,28 +1,27 @@
package org.parabot.environment.api.utils; package org.parabot.environment.api.utils;
/** /**
*
* A random class is used for generating random numbers * A random class is used for generating random numbers
* *
* @author Everel * @author Everel
*
*/ */
public class Random { public class Random {
private final static java.util.Random RANDOM = new java.util.Random(); private final static java.util.Random RANDOM = new java.util.Random();
/** /**
* Randomizes a number between minimum and maximum * Randomizes a number between minimum and maximum
* *
* @param min * @param min
* @param max * @param max
* @return randomized number *
*/ * @return randomized number
public static int between(final int min, final int max) { */
try { public static int between(final int min, final int max) {
return min + (max == min ? 0 : RANDOM.nextInt(max - min)); try {
} catch (Exception e) { return min + (max == min ? 0 : RANDOM.nextInt(max - min));
return min + (max - min); } catch (Exception e) {
} return min + (max - min);
} }
}
} }
@@ -3,66 +3,63 @@ package org.parabot.environment.api.utils;
import org.parabot.environment.scripts.framework.SleepCondition; import org.parabot.environment.scripts.framework.SleepCondition;
/** /**
*
* Holds various Time utilities * Holds various Time utilities
* *
* @author Everel * @author Everel
*
*/ */
public final class Time { public final class Time {
/** /**
* Sleeps for a given amount of time * Sleeps for a given amount of time
* @param ms *
*/ * @param ms
public static void sleep(final int ms) { */
try { public static void sleep(final int ms) {
Thread.sleep(ms); try {
} catch (InterruptedException e) { Thread.sleep(ms);
e.printStackTrace(); } catch (InterruptedException e) {
} e.printStackTrace();
} }
}
/**
* @param minumum
* @param maximum
*/
public static void sleep(final int minumum, final int maximum) {
try {
Thread.sleep(Random.between(minumum, maximum));
} catch (InterruptedException e) {
e.printStackTrace();
}
}
/** /**
* * Sleeps until the SleepCondition is valid.
* @param minumum *
* @param maximum * @param conn the condition.
*/ * @param timeout the time in miliseconds before it stops sleeping.
public static void sleep(final int minumum, final int maximum) { *
try { * @return whether it ran successfully without timing out.
Thread.sleep(Random.between(minumum, maximum)); */
} catch (InterruptedException e) { public static boolean sleep(SleepCondition conn, int timeout) {
e.printStackTrace(); long start = System.currentTimeMillis();
} while (!conn.isValid()) {
} if (start + timeout < System.currentTimeMillis()) {
return false;
}
Time.sleep(50);
}
return true;
}
/** /**
* Sleeps until the SleepCondition is valid. * Gets current time in milliseconds
* *
* @param conn * @return time in ms
* the condition. */
* @param timeout public static long get() {
* the time in miliseconds before it stops sleeping. return System.currentTimeMillis();
* @return whether it ran successfully without timing out. }
*/
public static boolean sleep(SleepCondition conn, int timeout) {
long start = System.currentTimeMillis();
while (!conn.isValid()) {
if (start + timeout < System.currentTimeMillis()) {
return false;
}
Time.sleep(50);
}
return true;
}
/**
* Gets current time in milliseconds
* @return time in ms
*/
public static long get() {
return System.currentTimeMillis();
}
} }
@@ -4,9 +4,8 @@ import org.parabot.core.ui.utils.UILog;
public class Version implements Comparable<Version> { public class Version implements Comparable<Version> {
private String version;
private static boolean notified; private static boolean notified;
private String version;
public Version(String version) { public Version(String version) {
if (version == null) { if (version == null) {
@@ -18,11 +17,24 @@ public class Version implements Comparable<Version> {
this.version = version; this.version = version;
} }
private static void notifyRC() {
if (!notified) {
UILog.log(
"Version warning",
"This is an RC version of Parabot\n" +
"This could be an unstable version of Parabot, and might crash at anytime\n\n" +
"If you find an error within the client, please report any at:\n" +
"https://github.com/Parabot/Parabot/issues"
);
notified = true;
}
}
public final String get() { public final String get() {
return this.version; return this.version;
} }
public boolean isNightly(){ public boolean isNightly() {
return this.version.contains("RC"); return this.version.contains("RC");
} }
@@ -39,7 +51,7 @@ public class Version implements Comparable<Version> {
String[] thisParts = this.get().split("\\."); String[] thisParts = this.get().split("\\.");
String[] thatParts = that.get().split("\\."); String[] thatParts = that.get().split("\\.");
int length = Math.max(thisParts.length, thatParts.length); int length = Math.max(thisParts.length, thatParts.length);
for (int i = 0; i < length; i++) { for (int i = 0; i < length; i++) {
int thisPart = i < thisParts.length ? int thisPart = i < thisParts.length ?
@@ -60,17 +72,4 @@ public class Version implements Comparable<Version> {
public boolean equals(Object that) { public boolean equals(Object that) {
return this == that || that != null && this.getClass() == that.getClass() && this.compareTo((Version) that) == 0; return this == that || that != null && this.getClass() == that.getClass() && this.compareTo((Version) that) == 0;
} }
private static void notifyRC() {
if (!notified) {
UILog.log(
"Version warning",
"This is an RC version of Parabot\n" +
"This could be an unstable version of Parabot, and might crash at anytime\n\n" +
"If you find an error within the client, please report any at:\n" +
"https://github.com/Parabot/Parabot/issues"
);
notified = true;
}
}
} }
@@ -1,225 +1,228 @@
package org.parabot.environment.input; package org.parabot.environment.input;
import java.awt.Component; import org.parabot.core.Context;
import java.awt.*;
import java.awt.event.KeyEvent; import java.awt.event.KeyEvent;
import java.awt.event.KeyListener; import java.awt.event.KeyListener;
import java.util.HashMap; import java.util.HashMap;
import java.util.Random; import java.util.Random;
import org.parabot.core.Context;
/** /**
*
* Virtual keyboard, dispatches key events to a component. * Virtual keyboard, dispatches key events to a component.
* *
* @author Everel, Matt, Dane * @author Everel, Matt, Dane
*
*/ */
public class Keyboard implements KeyListener { public class Keyboard implements KeyListener {
private static HashMap<Character, Character> specialChars; private static HashMap<Character, Character> specialChars;
private Component component;
private long pressTime;
public Keyboard(Component component) { static {
this.component = component; char[] spChars = { '~', '!', '@', '#', '%', '^', '&', '*', '(', ')',
} '_', '+', '{', '}', ':', '<', '>', '?', '"', '|' };
char[] replace = { '`', '1', '2', '3', '5', '6', '7', '8', '9', '0',
'-', '=', '[', ']', ';', ',', '.', '/', '\'', '\\' };
specialChars = new HashMap<Character, Character>(spChars.length);
for (int x = 0; x < spChars.length; ++x) {
specialChars.put(spChars[x], replace[x]);
}
}
public static Keyboard getInstance() { private Component component;
return Context.getInstance().getKeyboard(); private long pressTime;
}
static { public Keyboard(Component component) {
char[] spChars = { '~', '!', '@', '#', '%', '^', '&', '*', '(', ')', this.component = component;
'_', '+', '{', '}', ':', '<', '>', '?', '"', '|' }; }
char[] replace = { '`', '1', '2', '3', '5', '6', '7', '8', '9', '0',
'-', '=', '[', ']', ';', ',', '.', '/', '\'', '\\' };
specialChars = new HashMap<Character, Character>(spChars.length);
for (int x = 0; x < spChars.length; ++x)
specialChars.put(spChars[x], replace[x]);
}
private static long getRandom() { public static Keyboard getInstance() {
Random rand = new Random(); return Context.getInstance().getKeyboard();
return rand.nextInt(100) + 40; }
}
public void sendKeys(String s) { private static long getRandom() {
Random rand = new Random();
return rand.nextInt(100) + 40;
}
pressTime = System.currentTimeMillis(); public void sendKeys(String s) {
for (char c : s.toCharArray())
for (KeyEvent ke : createKeyClick(component, c)) {
try {
Thread.sleep(5);
} catch (InterruptedException e) {
e.printStackTrace();
}
sendKeyEvent(ke);
}
clickKey(10);
}
public void clickKey(char c) { pressTime = System.currentTimeMillis();
for (char c : s.toCharArray()) {
for (KeyEvent ke : createKeyClick(component, c)) {
try {
Thread.sleep(5);
} catch (InterruptedException e) {
e.printStackTrace();
}
sendKeyEvent(ke);
}
}
clickKey(10);
}
pressTime = System.currentTimeMillis(); public void clickKey(char c) {
for (KeyEvent ke : createKeyClick(component, c))
sendKeyEvent(ke);
}
public void clickKey(int keyCode) { pressTime = System.currentTimeMillis();
for (KeyEvent ke : createKeyClick(component, c)) {
sendKeyEvent(ke);
}
}
pressTime = System.currentTimeMillis(); public void clickKey(int keyCode) {
for (KeyEvent ke : createKeyClick(component, keyCode))
sendKeyEvent(ke);
}
public void pressKey(int keyCode) { pressTime = System.currentTimeMillis();
for (KeyEvent ke : createKeyClick(component, keyCode)) {
sendKeyEvent(ke);
}
}
pressTime = System.currentTimeMillis(); public void pressKey(int keyCode) {
KeyEvent ke = createKeyPress(component, keyCode);
sendKeyEvent(ke);
}
public void releaseKey(int keyCode) { pressTime = System.currentTimeMillis();
KeyEvent ke = createKeyPress(component, keyCode);
sendKeyEvent(ke);
}
pressTime = System.currentTimeMillis(); public void releaseKey(int keyCode) {
KeyEvent ke = createKeyRelease(component, keyCode);
sendKeyEvent(ke);
}
private KeyEvent[] createKeyClick(Component target, char c) { pressTime = System.currentTimeMillis();
KeyEvent ke = createKeyRelease(component, keyCode);
sendKeyEvent(ke);
}
pressTime += 2 * getRandom(); private KeyEvent[] createKeyClick(Component target, char c) {
Character newChar = specialChars.get(c); pressTime += 2 * getRandom();
int keyCode = Character.toUpperCase((newChar == null) ? c : newChar);
if (Character.isLowerCase(c) Character newChar = specialChars.get(c);
|| (!Character.isLetter(c) && (newChar == null))) { int keyCode = Character.toUpperCase((newChar == null) ? c : newChar);
KeyEvent pressed = new KeyEvent(target, KeyEvent.KEY_PRESSED,
pressTime, 0, keyCode, c);
KeyEvent typed = new KeyEvent(target, KeyEvent.KEY_TYPED,
pressTime, 0, 0, c);
pressTime += getRandom();
KeyEvent released = new KeyEvent(target, KeyEvent.KEY_RELEASED,
pressTime, 0, keyCode, c);
return new KeyEvent[] { pressed, typed, released }; if (Character.isLowerCase(c)
} else { || (!Character.isLetter(c) && (newChar == null))) {
KeyEvent shiftDown = new KeyEvent(target, KeyEvent.KEY_PRESSED, KeyEvent pressed = new KeyEvent(target, KeyEvent.KEY_PRESSED,
pressTime, KeyEvent.SHIFT_MASK, KeyEvent.VK_SHIFT, pressTime, 0, keyCode, c);
KeyEvent.CHAR_UNDEFINED); KeyEvent typed = new KeyEvent(target, KeyEvent.KEY_TYPED,
pressTime, 0, 0, c);
pressTime += getRandom();
KeyEvent released = new KeyEvent(target, KeyEvent.KEY_RELEASED,
pressTime, 0, keyCode, c);
pressTime += getRandom(); return new KeyEvent[]{ pressed, typed, released };
KeyEvent pressed = new KeyEvent(target, KeyEvent.KEY_PRESSED, } else {
pressTime, KeyEvent.SHIFT_MASK, keyCode, c); KeyEvent shiftDown = new KeyEvent(target, KeyEvent.KEY_PRESSED,
KeyEvent typed = new KeyEvent(target, KeyEvent.KEY_TYPED, pressTime, KeyEvent.SHIFT_MASK, KeyEvent.VK_SHIFT,
pressTime, KeyEvent.SHIFT_MASK, 0, c); KeyEvent.CHAR_UNDEFINED);
pressTime += getRandom();
KeyEvent released = new KeyEvent(target, KeyEvent.KEY_RELEASED,
pressTime, KeyEvent.SHIFT_MASK, keyCode, c);
pressTime += getRandom();
KeyEvent shiftUp = new KeyEvent(target, KeyEvent.KEY_RELEASED,
pressTime, 0, KeyEvent.VK_SHIFT, KeyEvent.CHAR_UNDEFINED);
return new KeyEvent[] { shiftDown, pressed, typed, released, pressTime += getRandom();
shiftUp }; KeyEvent pressed = new KeyEvent(target, KeyEvent.KEY_PRESSED,
} pressTime, KeyEvent.SHIFT_MASK, keyCode, c);
} KeyEvent typed = new KeyEvent(target, KeyEvent.KEY_TYPED,
pressTime, KeyEvent.SHIFT_MASK, 0, c);
pressTime += getRandom();
KeyEvent released = new KeyEvent(target, KeyEvent.KEY_RELEASED,
pressTime, KeyEvent.SHIFT_MASK, keyCode, c);
pressTime += getRandom();
KeyEvent shiftUp = new KeyEvent(target, KeyEvent.KEY_RELEASED,
pressTime, 0, KeyEvent.VK_SHIFT, KeyEvent.CHAR_UNDEFINED);
private KeyEvent[] createKeyClick(Component target, int keyCode) { return new KeyEvent[]{ shiftDown, pressed, typed, released,
int modifier = 0; shiftUp };
switch (keyCode) { }
case KeyEvent.VK_SHIFT: }
modifier = KeyEvent.SHIFT_MASK;
break;
case KeyEvent.VK_ALT:
modifier = KeyEvent.ALT_MASK;
break;
case KeyEvent.VK_CONTROL:
modifier = KeyEvent.CTRL_MASK;
break;
}
KeyEvent pressed = new KeyEvent(target, KeyEvent.KEY_PRESSED,
pressTime, modifier, keyCode, KeyEvent.CHAR_UNDEFINED);
KeyEvent released = new KeyEvent(target, KeyEvent.KEY_RELEASED,
pressTime + getRandom(), 0, keyCode, KeyEvent.CHAR_UNDEFINED);
return new KeyEvent[] { pressed, released }; private KeyEvent[] createKeyClick(Component target, int keyCode) {
} int modifier = 0;
switch (keyCode) {
case KeyEvent.VK_SHIFT:
modifier = KeyEvent.SHIFT_MASK;
break;
case KeyEvent.VK_ALT:
modifier = KeyEvent.ALT_MASK;
break;
case KeyEvent.VK_CONTROL:
modifier = KeyEvent.CTRL_MASK;
break;
}
KeyEvent pressed = new KeyEvent(target, KeyEvent.KEY_PRESSED,
pressTime, modifier, keyCode, KeyEvent.CHAR_UNDEFINED);
KeyEvent released = new KeyEvent(target, KeyEvent.KEY_RELEASED,
pressTime + getRandom(), 0, keyCode, KeyEvent.CHAR_UNDEFINED);
private KeyEvent createKeyPress(Component target, int keyCode) { return new KeyEvent[]{ pressed, released };
int modifier = 0; }
switch (keyCode) {
case KeyEvent.VK_SHIFT:
modifier = KeyEvent.SHIFT_MASK;
break;
case KeyEvent.VK_ALT:
modifier = KeyEvent.ALT_MASK;
break;
case KeyEvent.VK_CONTROL:
modifier = KeyEvent.CTRL_MASK;
break;
}
KeyEvent pressed = new KeyEvent(target, KeyEvent.KEY_PRESSED,
pressTime, modifier, keyCode, KeyEvent.CHAR_UNDEFINED);
return pressed; private KeyEvent createKeyPress(Component target, int keyCode) {
} int modifier = 0;
switch (keyCode) {
case KeyEvent.VK_SHIFT:
modifier = KeyEvent.SHIFT_MASK;
break;
case KeyEvent.VK_ALT:
modifier = KeyEvent.ALT_MASK;
break;
case KeyEvent.VK_CONTROL:
modifier = KeyEvent.CTRL_MASK;
break;
}
KeyEvent pressed = new KeyEvent(target, KeyEvent.KEY_PRESSED,
pressTime, modifier, keyCode, KeyEvent.CHAR_UNDEFINED);
private KeyEvent createKeyRelease(Component target, int keyCode) { return pressed;
@SuppressWarnings("unused") }
int modifier = 0;
switch (keyCode) {
case KeyEvent.VK_SHIFT:
modifier = KeyEvent.SHIFT_MASK;
break;
case KeyEvent.VK_ALT:
modifier = KeyEvent.ALT_MASK;
break;
case KeyEvent.VK_CONTROL:
modifier = KeyEvent.CTRL_MASK;
break;
}
KeyEvent released = new KeyEvent(target, KeyEvent.KEY_RELEASED,
pressTime + getRandom(), 0, keyCode, KeyEvent.CHAR_UNDEFINED);
return released; private KeyEvent createKeyRelease(Component target, int keyCode) {
} @SuppressWarnings("unused")
int modifier = 0;
switch (keyCode) {
case KeyEvent.VK_SHIFT:
modifier = KeyEvent.SHIFT_MASK;
break;
case KeyEvent.VK_ALT:
modifier = KeyEvent.ALT_MASK;
break;
case KeyEvent.VK_CONTROL:
modifier = KeyEvent.CTRL_MASK;
break;
}
KeyEvent released = new KeyEvent(target, KeyEvent.KEY_RELEASED,
pressTime + getRandom(), 0, keyCode, KeyEvent.CHAR_UNDEFINED);
public void sendKeyEvent(KeyEvent e) { return released;
for (KeyListener kl : component.getKeyListeners()) { }
if(kl instanceof Keyboard) {
continue;
}
if (!e.isConsumed()) {
switch (e.getID()) {
case KeyEvent.KEY_PRESSED:
kl.keyPressed(e);
break;
case KeyEvent.KEY_RELEASED:
kl.keyReleased(e);
break;
case KeyEvent.KEY_TYPED:
kl.keyTyped(e);
break;
}
}
}
}
@Override public void sendKeyEvent(KeyEvent e) {
public void keyPressed(KeyEvent e) { for (KeyListener kl : component.getKeyListeners()) {
if (kl instanceof Keyboard) {
continue;
}
if (!e.isConsumed()) {
switch (e.getID()) {
case KeyEvent.KEY_PRESSED:
kl.keyPressed(e);
break;
case KeyEvent.KEY_RELEASED:
kl.keyReleased(e);
break;
case KeyEvent.KEY_TYPED:
kl.keyTyped(e);
break;
}
}
}
}
} @Override
public void keyPressed(KeyEvent e) {
@Override }
public void keyReleased(KeyEvent e) {
} @Override
public void keyReleased(KeyEvent e) {
@Override }
public void keyTyped(KeyEvent e) {
} @Override
public void keyTyped(KeyEvent e) {
}
} }
@@ -9,155 +9,156 @@ import java.awt.event.MouseListener;
import java.awt.event.MouseMotionListener; import java.awt.event.MouseMotionListener;
/** /**
*
* A virtual mouse, dispatches mouse events to a component * A virtual mouse, dispatches mouse events to a component
* *
* @author Everel * @author Everel
*
*/ */
public class Mouse implements MouseListener, MouseMotionListener { public class Mouse implements MouseListener, MouseMotionListener {
private Component component; private Component component;
private int x; private int x;
private int y; private int y;
public Mouse(Component component) { public Mouse(Component component) {
this.component = component; this.component = component;
} }
public static Mouse getInstance() { public static Mouse getInstance() {
return Context.getInstance().getMouse(); return Context.getInstance().getMouse();
} }
/** /**
* Moves the mouse to the given point and clicks * Moves the mouse to the given point and clicks
* @param x *
* @param y * @param x
* @param left * @param y
*/ * @param left
public void click(final int x, final int y, final boolean left) { */
public void click(final int x, final int y, final boolean left) {
moveMouse(x, y); moveMouse(x, y);
Time.sleep(50, 200); Time.sleep(50, 200);
pressMouse(x, y, left); pressMouse(x, y, left);
Time.sleep(10, 100); Time.sleep(10, 100);
releaseMouse(x, y, left); releaseMouse(x, y, left);
Time.sleep(10, 100); Time.sleep(10, 100);
clickMouse(x, y, left); clickMouse(x, y, left);
} }
public void pressMouse(int x, int y, boolean left) { public void pressMouse(int x, int y, boolean left) {
MouseEvent me = new MouseEvent(component, MouseEvent me = new MouseEvent(component,
MouseEvent.MOUSE_PRESSED, System.currentTimeMillis(), 0, x, MouseEvent.MOUSE_PRESSED, System.currentTimeMillis(), 0, x,
y, 1, false, left ? MouseEvent.BUTTON1 : MouseEvent.BUTTON3); y, 1, false, left ? MouseEvent.BUTTON1 : MouseEvent.BUTTON3);
for(MouseListener l : component.getMouseListeners()) { for (MouseListener l : component.getMouseListeners()) {
if(!(l instanceof Mouse)) { if (!(l instanceof Mouse)) {
l.mousePressed(me); l.mousePressed(me);
} }
} }
} }
public void click(final Point p, final boolean left) { public void click(final Point p, final boolean left) {
click(p.x, p.y, left); click(p.x, p.y, left);
} }
public void click(final Point p) { public void click(final Point p) {
click(p.x, p.y, true); click(p.x, p.y, true);
} }
public void clickMouse(int x, int y, boolean left) { public void clickMouse(int x, int y, boolean left) {
try { try {
MouseEvent me = new MouseEvent(component, MouseEvent me = new MouseEvent(component,
MouseEvent.MOUSE_CLICKED, System.currentTimeMillis(), 0, x, MouseEvent.MOUSE_CLICKED, System.currentTimeMillis(), 0, x,
y, 0, false, left ? MouseEvent.BUTTON1 : MouseEvent.BUTTON3); y, 0, false, left ? MouseEvent.BUTTON1 : MouseEvent.BUTTON3);
for(MouseListener l : component.getMouseListeners()) { for (MouseListener l : component.getMouseListeners()) {
if(!(l instanceof Mouse)) { if (!(l instanceof Mouse)) {
l.mouseClicked(me); l.mouseClicked(me);
} }
} }
} catch (Exception e) { } catch (Exception e) {
e.printStackTrace(); e.printStackTrace();
} }
} }
public void releaseMouse(int x, int y, boolean left) { public void releaseMouse(int x, int y, boolean left) {
try { try {
MouseEvent me = new MouseEvent(component, MouseEvent me = new MouseEvent(component,
MouseEvent.MOUSE_RELEASED, System.currentTimeMillis(), 0, x, MouseEvent.MOUSE_RELEASED, System.currentTimeMillis(), 0, x,
y, 0, false, left ? MouseEvent.BUTTON1 : MouseEvent.BUTTON3); y, 0, false, left ? MouseEvent.BUTTON1 : MouseEvent.BUTTON3);
for(MouseListener l : component.getMouseListeners()) { for (MouseListener l : component.getMouseListeners()) {
if(!(l instanceof Mouse)) { if (!(l instanceof Mouse)) {
l.mouseReleased(me); l.mouseReleased(me);
} }
} }
} catch (Exception e) { } catch (Exception e) {
e.printStackTrace(); e.printStackTrace();
} }
} }
/** /**
* Moves the mouse cursor to the given location * Moves the mouse cursor to the given location
* @param x *
* @param y * @param x
*/ * @param y
public void moveMouse(int x, int y) { */
try { public void moveMouse(int x, int y) {
MouseEvent me = new MouseEvent(component, try {
MouseEvent.MOUSE_MOVED, System.currentTimeMillis(), 0, x, MouseEvent me = new MouseEvent(component,
y, 0, false); MouseEvent.MOUSE_MOVED, System.currentTimeMillis(), 0, x,
for(MouseMotionListener l : component.getMouseMotionListeners()) { y, 0, false);
if(!(l instanceof Mouse)) { for (MouseMotionListener l : component.getMouseMotionListeners()) {
l.mouseMoved(me); if (!(l instanceof Mouse)) {
} l.mouseMoved(me);
} }
} catch (Exception e) { }
e.printStackTrace(); } catch (Exception e) {
} e.printStackTrace();
} }
}
/** /**
* Mouse cursor current location * Mouse cursor current location
* @return point *
*/ * @return point
public Point getPoint() { */
return new Point(x, y); public Point getPoint() {
} return new Point(x, y);
}
@Override @Override
public void mouseMoved(MouseEvent e) { public void mouseMoved(MouseEvent e) {
x = e.getX(); x = e.getX();
y = e.getY(); y = e.getY();
} }
@Override @Override
public void mouseDragged(MouseEvent e) { public void mouseDragged(MouseEvent e) {
} }
@Override @Override
public void mouseClicked(MouseEvent e) { public void mouseClicked(MouseEvent e) {
} }
@Override @Override
public void mouseEntered(MouseEvent e) { public void mouseEntered(MouseEvent e) {
} }
@Override @Override
public void mouseExited(MouseEvent e) { public void mouseExited(MouseEvent e) {
} }
@Override @Override
public void mousePressed(MouseEvent e) { public void mousePressed(MouseEvent e) {
} }
@Override @Override
public void mouseReleased(MouseEvent e) { public void mouseReleased(MouseEvent e) {
} }
} }
@@ -48,6 +48,7 @@ public class RandomHandler {
/** /**
* @param random * @param random
*
* @deprecated * @deprecated
*/ */
@Deprecated @Deprecated
@@ -77,15 +78,6 @@ public class RandomHandler {
} }
} }
/**
* Sets the whole random arraylist to the arraylist given as argument
*
* @param randoms The new random arraylist
*/
public void setRandoms(ArrayList<Random> randoms) {
this.randoms = randoms;
}
/** /**
* Clears all added randoms * Clears all added randoms
*/ */
@@ -104,15 +96,16 @@ public class RandomHandler {
* Executes a specific random * Executes a specific random
* *
* @param r * @param r
*
* @return True if the random is executed, false if not * @return True if the random is executed, false if not
*/ */
public boolean executeRandom(Random r){ public boolean executeRandom(Random r) {
if (r.activate()) { if (r.activate()) {
Logger.addMessage("Running random '" + r.getName() + "'", true); Logger.addMessage("Running random '" + r.getName() + "'", true);
try { try {
r.execute(); r.execute();
return true; return true;
}catch (Exception e){ } catch (Exception e) {
Logger.addMessage("Random failed: '" + r.getName() + "'", false); Logger.addMessage("Random failed: '" + r.getName() + "'", false);
e.printStackTrace(); e.printStackTrace();
} }
@@ -126,7 +119,7 @@ public class RandomHandler {
* *
* @param type * @param type
*/ */
public void runAll(RandomType type){ public void runAll(RandomType type) {
for (Random r : this.activeRandoms) { for (Random r : this.activeRandoms) {
if (r.getRandomType().getId() == type.getId()) { if (r.getRandomType().getId() == type.getId()) {
executeRandom(r); executeRandom(r);
@@ -152,6 +145,7 @@ public class RandomHandler {
* Checks if random occurs and runs it * Checks if random occurs and runs it
* *
* @return returns <b>true</b> if a random has been executed, otherwise <b>false</b> * @return returns <b>true</b> if a random has been executed, otherwise <b>false</b>
*
* @see RandomHandler#checkAndRun(RandomType) * @see RandomHandler#checkAndRun(RandomType)
* @deprecated * @deprecated
*/ */
@@ -165,6 +159,15 @@ public class RandomHandler {
return this.randoms; return this.randoms;
} }
/**
* Sets the whole random arraylist to the arraylist given as argument
*
* @param randoms The new random arraylist
*/
public void setRandoms(ArrayList<Random> randoms) {
this.randoms = randoms;
}
public ArrayList<Random> getActiveRandoms() { public ArrayList<Random> getActiveRandoms() {
return this.activeRandoms; return this.activeRandoms;
} }
@@ -10,7 +10,7 @@ public enum RandomType {
ON_SERVER_START(2, "On server start"), ON_SERVER_START(2, "On server start"),
ON_SCRIPT_FINISH(3, "On script finish"); ON_SCRIPT_FINISH(3, "On script finish");
private int id; private int id;
private String name; private String name;
RandomType(int id, String name) { RandomType(int id, String name) {
@@ -18,6 +18,10 @@ public enum RandomType {
this.name = name; this.name = name;
} }
public static RandomType getDefault() {
return SCRIPT;
}
public int getId() { public int getId() {
return id; return id;
} }
@@ -25,8 +29,4 @@ public enum RandomType {
public String getName() { public String getName() {
return name; return name;
} }
public static RandomType getDefault() {
return SCRIPT;
}
} }
@@ -5,54 +5,53 @@ import org.parabot.core.ui.images.Images;
import java.awt.image.BufferedImage; import java.awt.image.BufferedImage;
import java.util.HashMap; import java.util.HashMap;
/** /**
*
* Holds script categories * Holds script categories
* *
* @author Dane, Paradox * @author Dane, Paradox
*
*/ */
public enum Category public enum Category {
{
AGILITY, COMBAT, COOKING, CRAFTING, CONSTRUCTION, DUNGEONEERING, FARMING, FIREMAKING, FISHING, FLETCHING, HERBLORE, HUNTER, MAGIC, MINIGAMES, MINING, MONEYMAKING, OTHER, PRAYER, RUNECRAFTING, SLAYER, SMITHING, THIEVING, UTILITY, WOODCUTTING; AGILITY, COMBAT, COOKING, CRAFTING, CONSTRUCTION, DUNGEONEERING, FARMING, FIREMAKING, FISHING, FLETCHING, HERBLORE, HUNTER, MAGIC, MINIGAMES, MINING, MONEYMAKING, OTHER, PRAYER, RUNECRAFTING, SLAYER, SMITHING, THIEVING, UTILITY, WOODCUTTING;
/** /**
* Gets image belonging to this category * Cache
* @return icon */
*/ private static HashMap<String, BufferedImage> images = new HashMap<>();
public BufferedImage getIcon() {
return Category.getIcon(this.name().toLowerCase());
}
/** static {
* Gets category icon image from filename images.put("script", Images.getResource("/storage/images/category/script.png"));
* @param s Name of the image - used for the hashmap index }
* @return icon
*/
public static BufferedImage getIcon(String s) {
if (images.get(s) == null) {
images.put(s, Images.getResource("/storage/images/category/" + s + ".png"));
}
return images.get(s);
}
@Override /**
public String toString() { * Gets category icon image from filename
StringBuilder b = new StringBuilder(); *
b.append(name().charAt(0)); * @param s Name of the image - used for the hashmap index
b.append(name().toLowerCase().substring(1)); *
return new String(b); * @return icon
} */
public static BufferedImage getIcon(String s) {
if (images.get(s) == null) {
images.put(s, Images.getResource("/storage/images/category/" + s + ".png"));
}
return images.get(s);
}
/** /**
* Cache * Gets image belonging to this category
*/ *
private static HashMap<String, BufferedImage> images = new HashMap<>(); * @return icon
*/
public BufferedImage getIcon() {
return Category.getIcon(this.name().toLowerCase());
}
static { @Override
images.put("script", Images.getResource("/storage/images/category/script.png")); public String toString() {
} StringBuilder b = new StringBuilder();
b.append(name().charAt(0));
b.append(name().toLowerCase().substring(1));
return new String(b);
}
} }

Some files were not shown because too many files have changed in this diff Show More