Skip to content

Instantly share code, notes, and snippets.

@NeatMonster
Last active September 2, 2024 08:56
Show Gist options
  • Save NeatMonster/842efa4a8955906136cbaccc9528c735 to your computer and use it in GitHub Desktop.
Save NeatMonster/842efa4a8955906136cbaccc9528c735 to your computer and use it in GitHub Desktop.
import java.io.BufferedReader;
import java.io.File;
import java.io.FileReader;
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;
import org.objectweb.asm.ClassVisitor;
import org.objectweb.asm.ClassWriter;
import org.objectweb.asm.commons.ClassRemapper;
import org.objectweb.asm.commons.Remapper;
import org.objectweb.asm.commons.SimpleRemapper;
import org.objectweb.asm.tree.ClassNode;
import me.lpk.util.JarUtils;
public class Renamer {
public static void main(String[] args) throws IOException {
File jarFile = new File(args[0]);
Map<String, ClassNode> nodes = JarUtils.loadClasses(jarFile);
Map<String, byte[]> out = JarUtils.loadNonClassEntries(jarFile);
Map<String, String> mappings = new HashMap<String, String>();
BufferedReader reader;
try {
reader = new BufferedReader(new FileReader(args[2]));
String line = reader.readLine();
while (line != null) {
String[] parts = line.split("=");
mappings.put(parts[0], parts[1]);
line = reader.readLine();
}
reader.close();
} catch (IOException e) {
e.printStackTrace();
}
out.putAll(process(nodes, mappings));
JarUtils.saveAsJar(out, args[1]);
}
static Map<String, byte[]> process(Map<String, ClassNode> nodes, Map<String, String> mappings) {
Map<String, byte[]> out = new HashMap<String, byte[]>();
Remapper mapper = new SimpleRemapper(mappings);
for (ClassNode cn : nodes.values()) {
ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS);
ClassVisitor remapper = new ClassRemapper(cw, mapper);
cn.accept(remapper);
String name = mappings.containsKey(cn.name) ? mappings.get(cn.name) : cn.name;
out.put(name + ".class", cw.toByteArray());
}
return out;
}
}
import os
import re
import sys
import lief
def deobfuscate(dexfull, jarfull):
print("[*] Analyzing %s" % dexfull)
mapping = {}
dex = lief.DEX.parse(dexfull)
for cls in dex.classes:
if not cls.source_filename:
continue
if not re.match('[a-z]{1,3}', cls.name):
continue
oldname = "%s/%s" % (cls.package_name, cls.name)
newname = "%s/%s" % (cls.package_name, cls.source_filename.rstrip(".java"))
if newname == oldname:
continue
if newname not in mapping:
mapping[newname] = []
mapping[newname].append(oldname)
if not mapping:
print("[*] Nothing to deobfuscate")
return jarfull
total = sum([len(l) for l in mapping.values()])
print("[*] Deobfuscating %d classes" % total)
txtfull = jarfull.replace(".jar", ".txt")
with open(txtfull, "w") as f:
for newname, oldnames in mapping.items():
for i, oldname in enumerate(sorted(oldnames)):
clsname = newname
if i > 0:
clsname = "%s$%d" % (newname, i + 1)
f.write("%s=%s\n" % (oldname, clsname))
newjarfull = jarfull.replace(".jar", "-deobf.jar")
os.system("java -jar ../Renamer.jar " + jarfull + " " + newjarfull + " " + txtfull + " >/dev/null 2>&1")
return newjarfull
s = sys.argv[1]
if ".git" in s:
exit()
apk = s + "/" + s + ".apk"
arm = s + "/oat/arm/" + s + ".odex"
arm64 = s + "/oat/arm64/" + s + ".odex"
outlib = s + "_lib"
outsrc = s + "_src"
dex = s + "_dex"
os.system("mkdir " + dex)
if os.path.exists(arm):
odex = arm
else:
odex = arm64
oat = lief.parse(odex)
for i, dexobj in enumerate(oat.dex_files):
dexfull = dex + "/classes.dex"
if i:
dexfull = dex + "/classes%d.dex" % (i + 1)
print("[*] Extracting %s from %s" % (dexfull, odex))
dexobj.save(dexfull)
for dexname in list(os.listdir(dex)):
dexfull = dex + "/" + dexname
jarfull = dex + "/" + os.path.splitext(dexname)[0] + ".jar"
print("[*] Converting %s to %s" % (dexfull, jarfull))
os.system("../dex-tools-2.1-SNAPSHOT/d2j-dex2jar.sh " + dexfull + " -o " + jarfull + " >/dev/null 2>&1")
jarfull = deobfuscate(dexfull, jarfull)
print("[*] Decompiling %s to %s" % (jarfull, outsrc))
os.system("java -jar ../procyon-decompiler-0.5.36.jar -mv -sm -jar " + jarfull + " -o " + outsrc + " >/dev/null 2>&1")
os.system("rm -rf " + dex)
tmp = s + "_tmp"
tmplib = tmp + "/lib"
os.system("mkdir " + tmp)
print("[*] Unzipping %s" % apk)
os.system("unzip " + apk + " -d " + tmp + " >/dev/null 2>&1")
if os.path.exists(tmplib):
print("[*] Copying libraries to %s" % outlib)
os.system("mv " + tmplib + " " + outlib)
os.system("rm -rf " + tmp)
os.system("rm -rf " + s)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment