Skip to content

Commit

Permalink
[POC] [Security Manager Replacement] GraalVM sandboxing
Browse files Browse the repository at this point in the history
Signed-off-by: Andriy Redko <[email protected]>
  • Loading branch information
reta committed Dec 17, 2024
1 parent ef44e86 commit 6201d8c
Show file tree
Hide file tree
Showing 22 changed files with 220 additions and 0 deletions.
43 changes: 43 additions & 0 deletions libs/espresso-sm/build.gradle
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
/*
* SPDX-License-Identifier: Apache-2.0
*
* The OpenSearch Contributors require contributions made to
* this file be licensed under the Apache-2.0 license or a
* compatible open source license.
*
* Modifications Copyright OpenSearch Contributors. See
* GitHub history for details.
*/

import org.opensearch.gradle.info.BuildParams

apply plugin: 'opensearch.publish'

base {
archivesName = 'esspresso-sm'
}

dependencies {
implementation "org.graalvm.polyglot:polyglot:24.0.2"
implementation "org.graalvm.sdk:nativeimage:24.0.2"
implementation "org.graalvm.sdk:collections:24.0.2"
implementation "org.graalvm.sdk:word:24.0.2"
implementation "org.graalvm.sdk:jniutils:24.0.2"
implementation "org.graalvm.llvm:llvm-api:24.0.2"
implementation "org.graalvm.llvm:llvm-language:24.0.2"
implementation "org.graalvm.llvm:llvm-language-native:24.0.2"
implementation "org.graalvm.llvm:llvm-language-native-resources:24.0.2"
implementation "org.graalvm.llvm:llvm-language-nfi:24.0.2"
implementation "org.graalvm.truffle:truffle-api:24.0.2"
implementation "org.graalvm.truffle:truffle-compiler:24.0.2"
implementation "org.graalvm.truffle:truffle-nfi:24.0.2"
implementation "org.graalvm.truffle:truffle-nfi-libffi:24.0.2"
implementation "org.graalvm.truffle:truffle-runtime:24.0.2"
implementation "org.graalvm.espresso:espresso-language:24.0.2"
implementation "org.graalvm.espresso:espresso-libs-resources-linux-amd64:24.0.2"
implementation "org.graalvm.espresso:espresso-runtime-resources-linux-amd64:24.0.2"
}

tasks.named('forbiddenApisMain').configure {
replaceSignatureFiles 'jdk-signatures'
}
1 change: 1 addition & 0 deletions libs/espresso-sm/licenses/collections-24.0.2.jar.sha1
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
bdb21160902f8c0e7014aa8bdbb37c10546c32d3
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
2e6b7b0643b7aaafe0a1a730834a3beb66eeabb6
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
14daa53850647f16e505ce23a72c0f2223ac2df0
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
b35e24aafc0e5e5b62fa112766194ba789d9a75c
1 change: 1 addition & 0 deletions libs/espresso-sm/licenses/jniutils-24.0.2.jar.sha1
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
d9d4eaf0a5c9108f6b8ebc61f19cdf37729ef9f2
1 change: 1 addition & 0 deletions libs/espresso-sm/licenses/llvm-api-24.0.2.jar.sha1
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
4f0cdc3ccd34eea004a5cace48d4edc605dc7a9a
1 change: 1 addition & 0 deletions libs/espresso-sm/licenses/llvm-language-24.0.2.jar.sha1
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
28ccc9c029b437cddb910c4cdd9d8fe86148d404
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
b52c4781fa9fda812011822ff10489190950443f
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
b0a849ec57bf3e4fc0f6e92070977ef0bd5f3570
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
52280dc5f2707cdfcb2ee44231869d2b88d47f7d
1 change: 1 addition & 0 deletions libs/espresso-sm/licenses/nativeimage-24.0.2.jar.sha1
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
bb27abb17f5edded52ebfb1dd34782db5a496ce2
1 change: 1 addition & 0 deletions libs/espresso-sm/licenses/polyglot-24.0.2.jar.sha1
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
c07243f549d629ba443655b45dce715d81d5e29c
1 change: 1 addition & 0 deletions libs/espresso-sm/licenses/truffle-api-24.0.2.jar.sha1
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
8242c9a693858fff8e1c3e27b6e4b32c03251aa2
1 change: 1 addition & 0 deletions libs/espresso-sm/licenses/truffle-compiler-24.0.2.jar.sha1
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
ea63dc2675fc98798486ea6d47d39a911b416435
1 change: 1 addition & 0 deletions libs/espresso-sm/licenses/truffle-nfi-24.0.2.jar.sha1
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
92aaaa8349645ed43b08c0b79881db539b831525
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
dafcf7e45574d1443cd587b28935c5dde7cd1f5c
1 change: 1 addition & 0 deletions libs/espresso-sm/licenses/truffle-runtime-24.0.2.jar.sha1
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
6b2cfb06b40fc4f273ed74b3303b21a432ae2e6c
1 change: 1 addition & 0 deletions libs/espresso-sm/licenses/word-24.0.2.jar.sha1
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
b927dbdc83ba16b3ccafc351a544d3d987124e92
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
package org.opensearch.espresso.sandbox;

import java.io.File;
import java.io.IOException;
import java.nio.file.Path;

import org.graalvm.polyglot.Context;
import org.graalvm.polyglot.Engine;
import org.graalvm.polyglot.HostAccess;
import org.graalvm.polyglot.PolyglotAccess;
import org.graalvm.polyglot.Value;
import org.graalvm.polyglot.io.IOAccess;

public class Sandbox {
public static void main(String[] args) throws IOException, InterruptedException {
final String opensearchHome = args[0];
System.out.println("OpenSearch home: " + opensearchHome);

final Engine engine = Engine.newBuilder().build();

System.out.println("Host JVM version: " + Runtime.version());
final String plugin = loadPlugin(opensearchHome, engine);
System.out.println(plugin);
}

public static String loadPlugin(String opensearchHome, Engine engine) throws IOException {
// See please:
// - https://github.com/oracle/graal/issues/10239
// -
// https://github.com/oracle/graal/blob/master/espresso/src/com.oracle.truffle.espresso/src/com/oracle/truffle/espresso/EspressoOptions.java
// -
// https://github.com/oracle/graal/blob/master/espresso/src/com.oracle.truffle.espresso.launcher/src/com/oracle/truffle/espresso/launcher/EspressoLauncher.java
final Context context = Context.newBuilder("java")
.option("java.JavaHome", "/usr/lib/jvm/java-21-openjdk-amd64/")
.option(
"java.Classpath",
("${opensearchHome}/lib/lucene-core-9.12.0.jar:"
+ "${opensearchHome}/lib/opensearch-cli-3.0.0-SNAPSHOT.jar:"
+ "${opensearchHome}/lib/jackson-core-2.17.2.jar:"
+ "${opensearchHome}/lib/jackson-dataformat-cbor-2.17.2.jar:"
+ "${opensearchHome}/lib/jackson-dataformat-smile-2.17.2.jar:"
+ "${opensearchHome}/lib/jackson-dataformat-yaml-2.17.2.jar:"
+ "${opensearchHome}/lib/snakeyaml-2.1.jar:"
+ "${opensearchHome}/lib/opensearch-3.0.0-SNAPSHOT.jar:"
+ "${opensearchHome}/lib/opensearch-core-3.0.0-SNAPSHOT.jar:"
+ "${opensearchHome}/lib/opensearch-common-3.0.0-SNAPSHOT.jar:"
+ "${opensearchHome}/lib/opensearch-x-content-3.0.0-SNAPSHOT.jar:"
+ "${opensearchHome}/lib/opensearch-secure-sm-3.0.0-SNAPSHOT.jar:"
+ "${opensearchHome}/lib/log4j-core-2.21.0.jar:"
+ "${opensearchHome}/lib/log4j-jul-2.21.0.jar:"
+ "${opensearchHome}/lib/log4j-api-2.21.0.jar:"
+ "${opensearchHome}/plugins/identity-shiro/slf4j-api-1.7.36.jar:"
+ "${opensearchHome}/plugins/identity-shiro/passay-1.6.3.jar:"
+ "${opensearchHome}/plugins/identity-shiro/identity-shiro-3.0.0-SNAPSHOT.jar:"
+ "${opensearchHome}/plugins/identity-shiro/shiro-core-1.13.0.jar").replaceAll(
"[$][{]opensearchHome[}]",
opensearchHome
)
)
.option("java.Properties.java.security.manager", "allow")
.allowNativeAccess(true)
.allowCreateThread(true)
.allowHostAccess(HostAccess.NONE)
.allowIO(IOAccess.NONE)
.allowPolyglotAccess(PolyglotAccess.newBuilder().allowBindingsAccess("java").build())
.engine(engine)
.build();

final Value runtime = context.getBindings("java").getMember("java.lang.Runtime");
System.out.println("Polyglot JVM version: " + runtime.invokeMember("version").toString());

final Path homePath = new File(opensearchHome).toPath();
final Path configPath = new File(opensearchHome + "/config").toPath();
context.getBindings("java")
.getMember("org.opensearch.bootstrap.QuickBoostrap")
.invokeMember("bootstrap", configPath.toString(), homePath.toString());

final Value securityManager = context.getBindings("java").getMember("java.lang.System").invokeMember("getSecurityManager");
System.out.println("Security Manager? " + securityManager.toString());

final Value settings = context.getBindings("java").getMember("org.opensearch.common.settings.Settings").getMember("EMPTY");
final Value result = context.getBindings("java").getMember("org.opensearch.identity.shiro.ShiroIdentityPlugin");
final Value instance = result.newInstance(settings);
System.out.println("Shiro Plugin? " + instance.toString());

final Value socket = instance.invokeMember("getSocket");
return socket.toString();
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,8 @@
import org.opensearch.threadpool.ThreadPool;
import org.opensearch.watcher.ResourceWatcherService;

import java.io.IOException;
import java.net.ServerSocket;
import java.util.Collection;
import java.util.Collections;
import java.util.function.Supplier;
Expand Down Expand Up @@ -138,6 +140,13 @@ public void handleRequest(RestRequest request, RestChannel channel, NodeClient c
}
}

/**
* Deliberately introducing the network access attempt to trigger SecurityException
*/
public ServerSocket getSocket() throws IOException {
return new ServerSocket(0);
}

public PluginSubject getPluginSubject(Plugin plugin) {
return new ShiroPluginSubject(threadPool);
}
Expand Down
60 changes: 60 additions & 0 deletions server/src/main/java/org/opensearch/bootstrap/QuickBoostrap.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
/*
* SPDX-License-Identifier: Apache-2.0
*
* The OpenSearch Contributors require contributions made to
* this file be licensed under the Apache-2.0 license or a
* compatible open source license.
*/

package org.opensearch.bootstrap;

import org.opensearch.cli.UserException;
import org.opensearch.common.logging.LogConfigurator;
import org.opensearch.common.settings.Settings;
import org.opensearch.env.Environment;
import org.opensearch.node.InternalSettingsPreparer;
import org.opensearch.node.Node;
import org.opensearch.node.NodeValidationException;

import java.nio.file.Paths;
import java.io.IOException;
import java.security.NoSuchAlgorithmException;
import java.util.Collections;

/**
* Quick bootstrap
*/
public class QuickBoostrap {
/**
* This method is invoked by {@link OpenSearch#main(String[])} to startup opensearch.
*/
public static void bootstrap(final String configPath, final String homePath) throws BootstrapException, NodeValidationException,
UserException {

// force the class initializer for BootstrapInfo to run before
// the security manager is installed
BootstrapInfo.init();

Settings settings = Settings.builder().put(Environment.PATH_HOME_SETTING.getKey(), homePath).build();
final Environment environment = InternalSettingsPreparer.prepareEnvironment(
settings,
Collections.emptyMap(),
Paths.get(configPath),
// HOSTNAME is set by opensearch-env and opensearch-env.bat so it is always available
() -> System.getenv("HOSTNAME")
);

LogConfigurator.setNodeName(Node.NODE_NAME_SETTING.get(environment.settings()));
try {
LogConfigurator.configure(environment);
} catch (IOException e) {
throw new BootstrapException(e);
}

try {
Security.configure(environment, BootstrapSettings.SECURITY_FILTER_BAD_DEFAULTS_SETTING.get(settings));
} catch (IOException | NoSuchAlgorithmException e) {
throw new BootstrapException(e);
}
}
}

0 comments on commit 6201d8c

Please sign in to comment.