Песочница против вредоносного кода в JAVA-приложении

Maven way

Если вы используете Maven, вы можете запустить следующую команду для запуска всех ваших тестовых случаев:

mvn clean test

Или вы можете запустить конкретный тест, как показано ниже

mvn clean test -Dtest=your.package.TestClassName
mvn clean test -Dtest=your.package.TestClassName#particularMethod

Если вы хотите увидеть трассировку стека (если есть) в консоли вместо файлов отчетов в папке target \ surefire-reports, установите для свойства user surefire.useFile значение false. Например:

mvn clean test -Dtest=your.package.TestClassName -Dsurefire.useFile=false

Gradle way

Если вы используете Gradle, вы можете запустить следующую команду для запуска всех ваших тестовых случаев:

gradle test

Или вы можете выполнить конкретный тест, как показано ниже

gradle test --tests your.package.TestClassName
gradle test --tests your.package.TestClassName.particularMethod

. Если вам нужна дополнительная информация, вы можете рассмотреть такие параметры, как -stacktrace или -info, или -debug.

Например, когда вы запускаете Gradle с уровнем ведения журнала информации --info, он покажет вам результат каждого теста во время работы. Если есть какое-либо исключение, оно покажет вам трассировку стека, указав, в чем проблема.

gradle test --info

Если вы хотите увидеть общие результаты теста, вы можете открыть отчет в браузере , например (открыть его с помощью Google Chrome в Ubuntu):

google-chrome build/reports/tests/index.html

Ant way

После того, как вы установили файл сборки build build.xml, вы можете запустить свой тест JUnit случаев из командной строки, как показано ниже:

ant -f build.xml 

Вы можете перейти по ссылке ниже, чтобы узнать больше о том, как настроить тесты JUnit в файле сборки Ant: https: //ant.apache. org / manual / Tasks / junit.html

Обычный способ

Если вы не используете Maven, Gradle или Ant, вы можете выполнить следующие действия:

Прежде всего, вам нужно скомпилировать ваши тестовые примеры. Например (в Linux):

javac -d /absolute/path/for/compiled/classes -cp /absolute/path/to/junit-4.12.jar /absolute/path/to/TestClassName.java

Затем запустите тестовые примеры. Например:

java -cp /absolute/path/for/compiled/classes:/absolute/path/to/junit-4.12.jar:/absolute/path/to/hamcrest-core-1.3.jar org.junit.runner.JUnitCore your.package.TestClassName

88
задан Alan Krueger 2 February 2009 в 04:50
поделиться

3 ответа

  1. Выполнение недоверяемый код в его собственном потоке. Это, например, предотвращает проблемы с бесконечными циклами и таким, и делает будущие шаги легче. Имейте основной поток, ожидают потока для окончания, и если занимает слишком много времени, уничтожьте его с Thread.stop. Thread.stop удерживается от использования, но так как недоверяемый код не должен иметь доступа ни к каким ресурсам, будет безопасно уничтожить его.

  2. Набор SecurityManager на том Потоке. Создайте подкласс SecurityManager, который переопределяет checkPermission (Разрешение перманент) для простого броска SecurityException для всех полномочий кроме выбора немногие. Существует список методов и полномочий, которых они требуют здесь: Полномочия в Java <глоток> ТМ 6 SDK.

  3. Использование пользовательский ClassLoder для загрузки недоверяемого кода. Ваш загрузчик класса требоваться все классы, которые использует недоверяемый код, таким образом, можно сделать, вещам нравится, отключают доступ к отдельным классам JDK. Нужно, имеют белый список позволенных классов JDK.

  4. Вы могли бы хотеть выполнить недоверяемый код в отдельной JVM. В то время как предыдущие шаги сделали бы код безопасным, существует одна раздражающая вещь, которую может все еще сделать изолированный код: выделите столько памяти, сколько она может, который заставляет видимое место главного приложения расти.

JSR 121: спецификация API Изоляции приложения была разработана для решения этого, но к сожалению она еще не имеет реализации.

Это - довольно подробная тема, и я главным образом пишу это все первое, что пришло на ум.

, Но так или иначе, некоторый имперфект, use-at-your-own-risk, вероятно, ошибочный (псевдо) код:

ClassLoder

class MyClassLoader extends ClassLoader {
  @Override
  public Class<?> loadClass(String name) throws ClassNotFoundException {
    if (name is white-listed JDK class) return super.loadClass(name);
    return findClass(name);
  }
  @Override
  public Class findClass(String name) {
    byte[] b = loadClassData(name);
    return defineClass(name, b, 0, b.length);
  }
  private byte[] loadClassData(String name) {
    // load the untrusted class data here
  }
}

Поток SecurityManager

class MySecurityManager extends SecurityManager {
  private Object secret;
  public MySecurityManager(Object pass) { secret = pass; }
  private void disable(Object pass) {
    if (pass == secret) secret = null;
  }
  // ... override checkXXX method(s) here.
  // Always allow them to succeed when secret==null
}

class MyIsolatedThread extends Thread {
  private Object pass = new Object();
  private MyClassLoader loader = new MyClassLoader();
  private MySecurityManager sm = new MySecurityManager(pass);
  public void run() {
    SecurityManager old = System.getSecurityManager();
    System.setSecurityManager(sm);
    runUntrustedCode();
    sm.disable(pass);
    System.setSecurityManager(old);
  }
  private void runUntrustedCode() {
    try {
      // run the custom class's main method for example:
      loader.loadClass("customclassname")
        .getMethod("main", String[].class)
        .invoke(null, new Object[]{...});
    } catch (Throwable t) {}
  }
}
107
ответ дан waqas 5 November 2019 в 15:11
поделиться

Очевидно, такая схема повышает все виды проблем безопасности. Java имеет строгую концепцию безопасности, но это не тривиально. Возможность завинчивания его и разрешения непривилегированному пользовательскому доступу жизненные компоненты системы не должна быть пропущена.

то, Что, предупреждая в стороне, если Вы берете ввод данных пользователем в форме исходного кода, первая вещь, необходимо сделать, скомпилировать его в байт-код Java. AFIAK, это не может быть сделано исходно, таким образом, необходимо будет сделать системный вызов javac и скомпилировать исходный код в байт-код на диске. Вот учебное руководство, которое может использоваться в качестве начальной точки для этого. Редактирование : как я узнал в комментариях, на самом деле можно скомпилировать код Java из источника исходно с помощью javax.tools. JavaCompiler

, После того как у Вас есть байт-код JVM, можно загрузить его в JVM с помощью ClassLoader функция defineClass. Для установки контекста защиты для этого загруженного класса, необходимо будет указать ProtectionDomain. Минимальный конструктор для ProtectionDomain требует и CodeSource и PermissionCollection. PermissionCollection является объектом основного использования Вам здесь - можно использовать его для определения точных полномочий, которые имеет загруженный класс. Эти полномочия должны быть в конечном счете осуществлены JVM AccessController.

существует много возможных точек ошибки здесь, и необходимо чрезвычайно стараться полностью понять все перед реализацией чего-либо.

18
ответ дан shsmurfy 5 November 2019 в 15:11
поделиться

Необходимо будет, вероятно, использовать пользовательское SecurityManger и/или AccessController. Для большого количества детали см. Архитектура безопасности Java и другая документация безопасности от Sun.

0
ответ дан Kieron 5 November 2019 в 15:11
поделиться
Другие вопросы по тегам:

Похожие вопросы: