fix(security): block build-tool and glibc env injection vectors in host exec sandbox (#49702)

Add GLIBC_TUNABLES, MAVEN_OPTS, SBT_OPTS, GRADLE_OPTS, ANT_OPTS,
DOTNET_ADDITIONAL_DEPS to blockedKeys and GRADLE_USER_HOME to
blockedOverrideKeys in the host exec security policy.

Closes #22681
This commit is contained in:
Andrew Demczuk 2026-03-18 13:11:01 +01:00 committed by GitHub
parent f58e0f5592
commit 089a43f5e8
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
4 changed files with 32 additions and 2 deletions

View File

@ -159,6 +159,7 @@ Docs: https://docs.openclaw.ai
- Tools/image generation: standardize the stock image create/edit path on the core `image_generate` tool. The old `nano-banana-pro` docs/examples are gone; if you previously copied that sample-skill config, switch to `agents.defaults.imageGenerationModel` for built-in image generation or install a separate third-party skill explicitly.
- Skills/image generation: remove the bundled `nano-banana-pro` skill wrapper. Use `agents.defaults.imageGenerationModel.primary: "google/gemini-3-pro-image-preview"` for the native Nano Banana-style path instead.
- Plugins/message discovery: require `ChannelMessageActionAdapter.describeMessageTool(...)` for shared `message` tool discovery. The legacy `listActions`, `getCapabilities`, and `getToolSchema` adapter methods are removed. Plugin authors should migrate message discovery to `describeMessageTool(...)` and keep channel-specific action runtime code inside the owning plugin package. Thanks @gumadeiras.
- Exec/env sandbox: block build-tool JVM injection (`MAVEN_OPTS`, `SBT_OPTS`, `GRADLE_OPTS`, `ANT_OPTS`), glibc tunable exploitation (`GLIBC_TUNABLES`), and .NET dependency resolution hijack (`DOTNET_ADDITIONAL_DEPS`) from the host exec environment, and restrict Gradle init script redirect (`GRADLE_USER_HOME`) as an override-only block so user-configured Gradle homes still propagate. (#49702)
## 2026.3.13

View File

@ -28,11 +28,18 @@ enum HostEnvSecurityPolicy {
"_JAVA_OPTIONS",
"JDK_JAVA_OPTIONS",
"PYTHONBREAKPOINT",
"DOTNET_STARTUP_HOOKS"
"DOTNET_STARTUP_HOOKS",
"DOTNET_ADDITIONAL_DEPS",
"GLIBC_TUNABLES",
"MAVEN_OPTS",
"SBT_OPTS",
"GRADLE_OPTS",
"ANT_OPTS"
]
static let blockedOverrideKeys: Set<String> = [
"HOME",
"GRADLE_USER_HOME",
"ZDOTDIR",
"GIT_SSH_COMMAND",
"GIT_SSH",

View File

@ -22,10 +22,17 @@
"_JAVA_OPTIONS",
"JDK_JAVA_OPTIONS",
"PYTHONBREAKPOINT",
"DOTNET_STARTUP_HOOKS"
"DOTNET_STARTUP_HOOKS",
"DOTNET_ADDITIONAL_DEPS",
"GLIBC_TUNABLES",
"MAVEN_OPTS",
"SBT_OPTS",
"GRADLE_OPTS",
"ANT_OPTS"
],
"blockedOverrideKeys": [
"HOME",
"GRADLE_USER_HOME",
"ZDOTDIR",
"GIT_SSH_COMMAND",
"GIT_SSH",

View File

@ -58,8 +58,21 @@ describe("isDangerousHostEnvVarName", () => {
expect(isDangerousHostEnvVarName("pythonbreakpoint")).toBe(true);
expect(isDangerousHostEnvVarName("DOTNET_STARTUP_HOOKS")).toBe(true);
expect(isDangerousHostEnvVarName("dotnet_startup_hooks")).toBe(true);
expect(isDangerousHostEnvVarName("DOTNET_ADDITIONAL_DEPS")).toBe(true);
expect(isDangerousHostEnvVarName("dotnet_additional_deps")).toBe(true);
expect(isDangerousHostEnvVarName("GLIBC_TUNABLES")).toBe(true);
expect(isDangerousHostEnvVarName("glibc_tunables")).toBe(true);
expect(isDangerousHostEnvVarName("MAVEN_OPTS")).toBe(true);
expect(isDangerousHostEnvVarName("maven_opts")).toBe(true);
expect(isDangerousHostEnvVarName("SBT_OPTS")).toBe(true);
expect(isDangerousHostEnvVarName("sbt_opts")).toBe(true);
expect(isDangerousHostEnvVarName("GRADLE_OPTS")).toBe(true);
expect(isDangerousHostEnvVarName("gradle_opts")).toBe(true);
expect(isDangerousHostEnvVarName("ANT_OPTS")).toBe(true);
expect(isDangerousHostEnvVarName("ant_opts")).toBe(true);
expect(isDangerousHostEnvVarName("PATH")).toBe(false);
expect(isDangerousHostEnvVarName("FOO")).toBe(false);
expect(isDangerousHostEnvVarName("GRADLE_USER_HOME")).toBe(false);
});
});
@ -197,6 +210,8 @@ describe("isDangerousHostEnvOverrideVarName", () => {
expect(isDangerousHostEnvOverrideVarName("editor")).toBe(true);
expect(isDangerousHostEnvOverrideVarName("NPM_CONFIG_USERCONFIG")).toBe(true);
expect(isDangerousHostEnvOverrideVarName("git_config_global")).toBe(true);
expect(isDangerousHostEnvOverrideVarName("GRADLE_USER_HOME")).toBe(true);
expect(isDangerousHostEnvOverrideVarName("gradle_user_home")).toBe(true);
expect(isDangerousHostEnvOverrideVarName("BASH_ENV")).toBe(false);
expect(isDangerousHostEnvOverrideVarName("FOO")).toBe(false);
});