diff --git a/deobfuscator/src/test/java/net/runelite/runesuite/HookImporter.java b/deobfuscator/src/test/java/net/runelite/runesuite/HookImporter.java index 137260e925..c4a7892a1f 100644 --- a/deobfuscator/src/test/java/net/runelite/runesuite/HookImporter.java +++ b/deobfuscator/src/test/java/net/runelite/runesuite/HookImporter.java @@ -52,6 +52,7 @@ import net.runelite.deob.util.JarUtil; import net.runelite.deob.util.NameMappings; import org.junit.After; import org.junit.Before; +import org.junit.Ignore; import org.junit.Rule; import org.junit.Test; import org.junit.rules.TemporaryFolder; @@ -87,12 +88,13 @@ public class HookImporter @After public void after() throws IOException { - File out = new File("C:/Users/Lucas/Desktop/client.jar"); + File out = folder.newFile("client.jar"); JarUtil.saveJar(group, out); logger.info("Wrote to {}", out); } @Test + @Ignore public void importHooks() { int classes = 0, fields = 0, methods = 0, access = 0; diff --git a/deobfuscator/src/test/resources/deob-test.properties b/deobfuscator/src/test/resources/deob-test.properties index 125bd16ceb..e26a22a2b9 100644 --- a/deobfuscator/src/test/resources/deob-test.properties +++ b/deobfuscator/src/test/resources/deob-test.properties @@ -1,3 +1,3 @@ -rs.client=C:/Users/Lucas/Desktop/gamepack180_deob.jar +rs.client=${net.runelite.rs:rs-client:jar} rs.version=180 vanilla.client=${net.runelite.rs:vanilla:jar} \ No newline at end of file diff --git a/injector-plugin/src/main/java/net/runelite/injector/Inject.java b/injector-plugin/src/main/java/net/runelite/injector/Inject.java index af5322e60c..53f1c40cc4 100644 --- a/injector-plugin/src/main/java/net/runelite/injector/Inject.java +++ b/injector-plugin/src/main/java/net/runelite/injector/Inject.java @@ -303,7 +303,7 @@ public class Inject apiMethod = findImportMethodOnApi(targetApiClass, exportedName, false); if (apiMethod == null) { - // logger.debug("Unable to find import method on api class {} with imported name {}, not injecting getter", targetApiClass, exportedName); + //logger.debug("Unable to find import method on api class {} with imported name {}, not injecting getter", targetApiClass, exportedName); continue; } diff --git a/injector-plugin/src/main/java/net/runelite/injector/InjectHook.java b/injector-plugin/src/main/java/net/runelite/injector/InjectHook.java index a89c8019bf..4be2f1cb5c 100644 --- a/injector-plugin/src/main/java/net/runelite/injector/InjectHook.java +++ b/injector-plugin/src/main/java/net/runelite/injector/InjectHook.java @@ -41,9 +41,11 @@ import net.runelite.asm.attributes.code.instruction.types.SetFieldInstruction; import net.runelite.asm.attributes.code.instructions.ArrayStore; import net.runelite.asm.attributes.code.instructions.CheckCast; import net.runelite.asm.attributes.code.instructions.Dup; +import net.runelite.asm.attributes.code.instructions.IMul; import net.runelite.asm.attributes.code.instructions.InvokeStatic; import net.runelite.asm.attributes.code.instructions.InvokeVirtual; import net.runelite.asm.attributes.code.instructions.LDC; +import net.runelite.asm.attributes.code.instructions.LMul; import net.runelite.asm.attributes.code.instructions.PutField; import net.runelite.asm.attributes.code.instructions.Swap; import net.runelite.asm.execution.Execution; @@ -63,6 +65,7 @@ public class InjectHook String clazz; Method method; boolean before; + Number getter; } private static final String HOOK_METHOD_SIGNATURE = "(I)V"; @@ -154,7 +157,7 @@ public class InjectHook } else { - // idx + 1 to insert after the set + // idx + 1 to insert after the set injectCallback(ins, idx + 1, hookInfo, null, objectStackContext); } } @@ -262,6 +265,21 @@ public class InjectHook ins.getInstructions().add(idx++, new Dup(ins)); // dup value idx = recursivelyPush(ins, idx, object); ins.getInstructions().add(idx++, new Swap(ins)); + if (hookInfo.getter != null) + { + assert hookInfo.getter instanceof Integer || hookInfo.getter instanceof Long; + + if (hookInfo.getter instanceof Integer) + { + ins.getInstructions().add(idx++, new LDC(ins, (int) hookInfo.getter)); + ins.getInstructions().add(idx++,new IMul(ins)); + } + else + { + ins.getInstructions().add(idx++, new LDC(ins, (long) hookInfo.getter)); + ins.getInstructions().add(idx++, new LMul(ins)); + } + } if (!value.type.equals(methodArgumentType)) { CheckCast checkCast = new CheckCast(ins); diff --git a/injector-plugin/src/main/java/net/runelite/injector/MixinInjector.java b/injector-plugin/src/main/java/net/runelite/injector/MixinInjector.java index 9e4b64cacb..032524878a 100644 --- a/injector-plugin/src/main/java/net/runelite/injector/MixinInjector.java +++ b/injector-plugin/src/main/java/net/runelite/injector/MixinInjector.java @@ -909,6 +909,13 @@ public class MixinInjector throw new InjectionException("Field hook for nonexistent field " + hookName + " on " + method); } + Annotation an = targetField.getAnnotations().find(DeobAnnotations.OBFUSCATED_GETTER); + Number getter = null; + if (an != null) + { + getter = (Number) an.getElement().getValue(); + } + Field obField = inject.toObField(targetField); if (method.isStatic() != targetField.isStatic()) @@ -922,6 +929,7 @@ public class MixinInjector hookInfo.fieldName = hookName; hookInfo.method = method; hookInfo.before = before; + hookInfo.getter = getter; injectHook.hook(obField, hookInfo); } } diff --git a/runelite-client/src/main/java/net/runelite/client/plugins/spellbook/SpellbookPlugin.java b/runelite-client/src/main/java/net/runelite/client/plugins/spellbook/SpellbookPlugin.java index 5ea8dc7cc9..5f739ab8b5 100644 --- a/runelite-client/src/main/java/net/runelite/client/plugins/spellbook/SpellbookPlugin.java +++ b/runelite-client/src/main/java/net/runelite/client/plugins/spellbook/SpellbookPlugin.java @@ -448,9 +448,7 @@ public class SpellbookPlugin extends Plugin } // CHECKSTYLE:OFF - Collection gson = GSON.fromJson(cfg, new TypeToken>() - { - }.getType()); + Collection gson = GSON.fromJson(cfg, new TypeToken>() {}.getType()); // CHECKSTYLE:ON gson.stream().filter(Objects::nonNull).forEach(s -> spells.put(s.getWidget(), s)); @@ -465,7 +463,7 @@ public class SpellbookPlugin extends Plugin private void saveSpells() { - if (spells.isEmpty()) + if (spells.isEmpty() || tmp == null || tmp.isEmpty()) { return; } diff --git a/runelite-client/src/main/java/net/runelite/client/rs/ClientLoader.java b/runelite-client/src/main/java/net/runelite/client/rs/ClientLoader.java index 58e58d5874..027eaeda37 100644 --- a/runelite-client/src/main/java/net/runelite/client/rs/ClientLoader.java +++ b/runelite-client/src/main/java/net/runelite/client/rs/ClientLoader.java @@ -222,7 +222,7 @@ public class ClientLoader if (rs instanceof Client) { - log.info("client-patch {}", "420 blaze it RL pricks"); + log.info("client-patch 420 blaze it RL pricks"); } return rs; @@ -274,7 +274,7 @@ public class ClientLoader { FileOutputStream fileOutputStream = new FileOutputStream(INJECTED_CLIENT); fileOutputStream.getChannel() - .transferFrom(readableByteChannel, 0, Long.MAX_VALUE); + .transferFrom(readableByteChannel, 0, Integer.MAX_VALUE); } catch (IOException e) { diff --git a/runelite-mixins/src/main/java/net/runelite/mixins/RSWidgetMixin.java b/runelite-mixins/src/main/java/net/runelite/mixins/RSWidgetMixin.java index 8fa4f2ba2c..4c59a88e53 100644 --- a/runelite-mixins/src/main/java/net/runelite/mixins/RSWidgetMixin.java +++ b/runelite-mixins/src/main/java/net/runelite/mixins/RSWidgetMixin.java @@ -258,6 +258,11 @@ public abstract class RSWidgetMixin implements RSWidget for (int i = 0; i < itemIds.length; ++i) { + if (itemIds[i] <= 0) + { + continue; + } + WidgetItem item = getWidgetItem(i); if (item != null) @@ -287,19 +292,17 @@ public abstract class RSWidgetMixin implements RSWidget int itemId = itemIds[index]; int itemQuantity = itemQuantities[index]; - Point widgetCanvasLocation = getCanvasLocation(); - - if (itemId <= 0 || itemQuantity <= 0 || columns <= 0) + if (columns <= 0) { return null; } int row = index / columns; int col = index % columns; - int itemX = widgetCanvasLocation.getX() + ((ITEM_SLOT_SIZE + xPitch) * col); - int itemY = widgetCanvasLocation.getY() + ((ITEM_SLOT_SIZE + yPitch) * row); + int itemX = rl$x + ((ITEM_SLOT_SIZE + xPitch) * col); + int itemY = rl$y + ((ITEM_SLOT_SIZE + yPitch) * row); - Rectangle bounds = new Rectangle(itemX - 1, itemY - 1, ITEM_SLOT_SIZE, ITEM_SLOT_SIZE); + Rectangle bounds = new Rectangle(itemX, itemY, ITEM_SLOT_SIZE, ITEM_SLOT_SIZE); return new WidgetItem(itemId - 1, itemQuantity, index, bounds, this); } diff --git a/runescape-client/src/main/java/Client.java b/runescape-client/src/main/java/Client.java index 1cd0f225ca..12fa080705 100644 --- a/runescape-client/src/main/java/Client.java +++ b/runescape-client/src/main/java/Client.java @@ -4710,7 +4710,7 @@ public final class Client extends GameShell implements Usernamed { int var8; if(!isMenuOpen) { if(__client_lq != -1) { - class39.method741(__client_lq, __client_ln); + class39.drawMenuActionTextAt(__client_lq, __client_ln); } } else { var1 = class25.menuX; diff --git a/runescape-client/src/main/java/class39.java b/runescape-client/src/main/java/class39.java index 3d56e1aaf4..9e05f0cb77 100644 --- a/runescape-client/src/main/java/class39.java +++ b/runescape-client/src/main/java/class39.java @@ -767,7 +767,8 @@ public class class39 extends class21 { signature = "(IIB)V", garbageValue = "3" ) - static final void method741(int var0, int var1) { + @Export("drawMenuActionTextAt") + static final void drawMenuActionTextAt(int var0, int var1) { if(Client.menuOptionsCount >= 2 || Client.isItemSelected != 0 || Client.isSpellSelected) { if(Client.showMouseOverText) { int var2 = Client.menuOptionsCount - 1; @@ -790,10 +791,10 @@ public class class39 extends class21 { } if(Client.menuOptionsCount > 2) { - var4 = var4 + BufferedFile.colorStartTag(16777215) + " " + '/' + " " + (Client.menuOptionsCount - 2) + " more options"; + var4 = var4 + BufferedFile.colorStartTag(0xffffff) + " " + '/' + " " + (Client.menuOptionsCount - 2) + " more options"; } - class2.fontBold12.drawRandomAlphaAndSpacing(var4, var0 + 4, var1 + 15, 16777215, 0, Client.cycle / 1000); + class2.fontBold12.drawRandomAlphaAndSpacing(var4, var0 + 4, var1 + 15, 0xffffff, 0, Client.cycle / 1000); } } }