Smarter Security Manager

Removed the blocking concept and replaced with a hardcoded whitelist
This commit is contained in:
Konloch 2021-07-19 08:39:59 -07:00
parent b7b72f957f
commit 74c88d3933
9 changed files with 44 additions and 83 deletions

View file

@ -59,16 +59,12 @@ public class Constants
{
new Thread(()->{
try {
BytecodeViewer.sm.pauseBlocking();
// Hide file by running attrib system command (on Windows)
Process p = new ProcessBuilder("attrib",
"+H",
BCVDir.getAbsolutePath()).start();
} catch (Exception e) {
//ignore
} finally {
BytecodeViewer.sm.resumeBlocking();
}
}, "Hide BCV Dir").start();
}

View file

@ -70,7 +70,6 @@ public class JavaCompiler extends InternalCompiler
boolean cont = true;
try {
BytecodeViewer.sm.pauseBlocking();
StringBuilder log = new StringBuilder();
ProcessBuilder pb;
@ -143,8 +142,6 @@ public class JavaCompiler extends InternalCompiler
} catch (Exception e) {
cont = false;
e.printStackTrace();
} finally {
BytecodeViewer.sm.resumeBlocking();
}
cp.delete();

View file

@ -69,8 +69,6 @@ public class KrakatauAssembler extends InternalCompiler
try
{
BytecodeViewer.sm.pauseBlocking();
String[] pythonCommands = new String[]{Configuration.python2};
if(!Configuration.python2Extra.isEmpty())
pythonCommands = ArrayUtils.addAll(pythonCommands, Configuration.python2Extra);
@ -120,8 +118,6 @@ public class KrakatauAssembler extends InternalCompiler
} catch (Exception e) {
e.printStackTrace();
//BytecodeViewer.handleException(log.toString());
} finally {
BytecodeViewer.sm.resumeBlocking();
}
return null;

View file

@ -92,8 +92,6 @@ public class KrakatauDecompiler extends InternalDecompiler
String s = ExceptionUI.SEND_STACKTRACE_TO_NL;
try {
BytecodeViewer.sm.pauseBlocking();
String[] pythonCommands = new String[]{Configuration.python2};
if(!Configuration.python2Extra.isEmpty())
pythonCommands = ArrayUtils.addAll(pythonCommands, Configuration.python2Extra);
@ -145,8 +143,6 @@ public class KrakatauDecompiler extends InternalDecompiler
e.printStackTrace(new PrintWriter(sw));
e.printStackTrace();
s += nl + ExceptionUI.SEND_STACKTRACE_TO_NL + sw;
} finally {
BytecodeViewer.sm.resumeBlocking();
}
return s;
@ -180,8 +176,6 @@ public class KrakatauDecompiler extends InternalDecompiler
JarUtils.saveAsJarClassesOnly(BytecodeViewer.getLoadedClasses(), tempJar.getAbsolutePath());
try {
BytecodeViewer.sm.pauseBlocking();
String[] pythonCommands = new String[]{Configuration.python2};
if(!Configuration.python2Extra.isEmpty())
pythonCommands = ArrayUtils.addAll(pythonCommands, Configuration.python2Extra);
@ -236,8 +230,6 @@ public class KrakatauDecompiler extends InternalDecompiler
e.printStackTrace(new PrintWriter(sw));
e.printStackTrace();
s += nl + ExceptionUI.SEND_STACKTRACE_TO_NL + sw;
} finally {
BytecodeViewer.sm.resumeBlocking();
}
return s;
@ -262,8 +254,6 @@ public class KrakatauDecompiler extends InternalDecompiler
final File tempJar = new File(sourceJar);
try {
BytecodeViewer.sm.pauseBlocking();
String[] pythonCommands = new String[]{Configuration.python2};
if(!Configuration.python2Extra.isEmpty())
pythonCommands = ArrayUtils.addAll(pythonCommands, Configuration.python2Extra);
@ -289,8 +279,6 @@ public class KrakatauDecompiler extends InternalDecompiler
ZipUtils.zipFolder(tempDirectory.getAbsolutePath(), zipName, ran);
} catch (Exception e) {
BytecodeViewer.handleException(e);
} finally {
BytecodeViewer.sm.resumeBlocking();
}
}
}

View file

@ -61,8 +61,6 @@ public class KrakatauDisassembler extends InternalDecompiler
JarUtils.saveAsJarClassesOnly(BytecodeViewer.getLoadedClasses(), tempJar.getAbsolutePath());
try {
BytecodeViewer.sm.pauseBlocking();
String[] pythonCommands = new String[]{Configuration.python2};
if(!Configuration.python2Extra.isEmpty())
pythonCommands = ArrayUtils.addAll(pythonCommands, Configuration.python2Extra);
@ -112,8 +110,6 @@ public class KrakatauDisassembler extends InternalDecompiler
e.printStackTrace(new PrintWriter(sw));
e.printStackTrace();
s += nl + ExceptionUI.SEND_STACKTRACE_TO_NL + sw;
} finally {
BytecodeViewer.sm.resumeBlocking();
}
return s;
}
@ -130,8 +126,6 @@ public class KrakatauDisassembler extends InternalDecompiler
final File tempJar = new File(sourceJar);
try {
BytecodeViewer.sm.pauseBlocking();
String[] pythonCommands = new String[]{Configuration.python2};
if(!Configuration.python2Extra.isEmpty())
pythonCommands = ArrayUtils.addAll(pythonCommands, Configuration.python2Extra);
@ -154,8 +148,6 @@ public class KrakatauDisassembler extends InternalDecompiler
ZipUtils.zipFolder(tempDirectory.getAbsolutePath(), zipName, ran);
} catch (Exception e) {
BytecodeViewer.handleException(e);
} finally {
BytecodeViewer.sm.resumeBlocking();
}
}
}

View file

@ -12,7 +12,6 @@ import java.io.BufferedReader;
import java.io.File;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.Objects;
import the.bytecode.club.bytecodeviewer.util.MiscUtils;
import static the.bytecode.club.bytecodeviewer.Constants.*;
@ -360,10 +359,7 @@ public class ExternalResources
if(!executedClass.equals(ExternalResources.class.getCanonicalName()))
return;
try
{
BytecodeViewer.sm.pauseBlocking();
try {
//read the version output
ProcessBuilder pb = new ProcessBuilder(command);
Process p = pb.start();
@ -372,12 +368,7 @@ public class ExternalResources
//check for matching text
if(readProcess(p).toLowerCase().contains(matchingText))
onMatch.run();
}
catch (Exception e) { } //ignore
finally
{
BytecodeViewer.sm.resumeBlocking();
}
} catch (Exception e) { } //ignore
}
/**

View file

@ -69,10 +69,8 @@ public class APKTool {
//save entire jar as smali files
System.out.println("Building!");
BytecodeViewer.sm.pauseBlocking();
brut.apktool.Main.main(new String[]{"b", container.APKToolContents.getAbsolutePath(), "--frame-path",
tempAPKPath.getAbsolutePath(), "-o", output.getAbsolutePath()});
BytecodeViewer.sm.resumeBlocking();
tempAPKPath.delete();
} catch (Exception e) {
BytecodeViewer.handleException(e);

View file

@ -46,7 +46,6 @@ public class Enjarify {
return;
try {
BytecodeViewer.sm.pauseBlocking();
ProcessBuilder pb = new ProcessBuilder(
Configuration.python3,
"-O",
@ -102,8 +101,6 @@ public class Enjarify {
} catch (Exception e) {
BytecodeViewer.handleException(e);
} finally {
BytecodeViewer.sm.resumeBlocking();
}
}
}

View file

@ -39,7 +39,6 @@ import java.util.concurrent.atomic.AtomicInteger;
public class SecurityMan extends SecurityManager
{
private AtomicInteger blocking = new AtomicInteger(1); //TODO replace with a more secure system
private AtomicInteger silentExec = new AtomicInteger(1);
private boolean printing = false;
private boolean printingPackage = false;
@ -48,36 +47,6 @@ public class SecurityMan extends SecurityManager
silentExec.addAndGet(b ? 1 : -1);
}
public void resumeBlocking() {
blocking.incrementAndGet();
}
//slightly safer security system than just a public static boolean being toggled
public void pauseBlocking()
{
String executedClass = Thread.currentThread().getStackTrace()[2].getClassName();
if (executedClass.equals(KrakatauDecompiler.class.getCanonicalName()) ||
executedClass.equals(KrakatauDisassembler.class.getCanonicalName()) ||
executedClass.equals(CFRDecompiler.class.getCanonicalName()) ||
executedClass.equals(ProcyonDecompiler.class.getCanonicalName()) ||
executedClass.equals(FernFlowerDecompiler.class.getCanonicalName()) ||
executedClass.equals(JDGUIDecompiler.class.getCanonicalName()) ||
executedClass.equals(KrakatauAssembler.class.getCanonicalName()) ||
executedClass.equals(ExternalResources.class.getCanonicalName()) ||
executedClass.equals(Enjarify.class.getCanonicalName()) ||
executedClass.equals(APKTool.class.getCanonicalName()) ||
executedClass.equals(BytecodeViewer.class.getCanonicalName()) ||
executedClass.equals(Constants.class.getCanonicalName()) ||
executedClass.equals(JavaCompiler.class.getCanonicalName()))
{
blocking.decrementAndGet();
}
else for (StackTraceElement stackTraceElements : Thread.currentThread().getStackTrace())
{
System.out.println(stackTraceElements.getClassName());
}
}
public void setPrinting(boolean printing)
{
this.printing = printing;
@ -89,8 +58,10 @@ public class SecurityMan extends SecurityManager
}
@Override
public void checkExec(String cmd) {
String[] whitelist = {
public void checkExec(String cmd)
{
String[] whitelist =
{
"attrib",
"python",
"pypy",
@ -101,17 +72,52 @@ public class SecurityMan extends SecurityManager
String lowerCaseCMD = cmd.toLowerCase();
for (String s : whitelist)
if (lowerCaseCMD.contains(s)) {
if (lowerCaseCMD.contains(s))
{
allow = true;
break;
}
if (allow && blocking.get() <= 0)
boolean validClassCall = false;
if(canClassExecute(Thread.currentThread().getStackTrace()[3].getClassName()))
validClassCall = true;
else if(canClassExecute(Thread.currentThread().getStackTrace()[6].getClassName()))
validClassCall = true;
else
{
int index = 0;
for (StackTraceElement stackTraceElements : Thread.currentThread().getStackTrace())
{
System.out.println(index++ + ":" + stackTraceElements.getClassName());
}
}
if (allow && validClassCall)
{
if(silentExec.get() >= 1)
System.err.println("Allowing exec: " + cmd);
}
else throw new SecurityException("BCV is awesome, blocking(" + blocking + ") exec " + cmd);
else throw new SecurityException("BCV is awesome! Blocking exec: " + cmd);
}
/**
* Execute Whitelist goes here
*/
private boolean canClassExecute(String fullyQualifiedClassName)
{
return fullyQualifiedClassName.equals(KrakatauDecompiler.class.getCanonicalName()) ||
fullyQualifiedClassName.equals(KrakatauDisassembler.class.getCanonicalName()) ||
fullyQualifiedClassName.equals(CFRDecompiler.class.getCanonicalName()) ||
fullyQualifiedClassName.equals(ProcyonDecompiler.class.getCanonicalName()) ||
fullyQualifiedClassName.equals(FernFlowerDecompiler.class.getCanonicalName()) ||
fullyQualifiedClassName.equals(JDGUIDecompiler.class.getCanonicalName()) ||
fullyQualifiedClassName.equals(KrakatauAssembler.class.getCanonicalName()) ||
fullyQualifiedClassName.equals(ExternalResources.class.getCanonicalName()) ||
fullyQualifiedClassName.equals(Enjarify.class.getCanonicalName()) ||
fullyQualifiedClassName.equals(APKTool.class.getCanonicalName()) ||
fullyQualifiedClassName.equals(BytecodeViewer.class.getCanonicalName()) ||
fullyQualifiedClassName.equals(Constants.class.getCanonicalName()) ||
fullyQualifiedClassName.equals(JavaCompiler.class.getCanonicalName());
}
@Override