agent: raise regorus policy length limits

regorus 0.9.0 introduced a hard, per-engine ceiling on parsed-policy
size (1024 columns / 1 MiB / 20 000 lines, see lexer.rs:30 in
microsoft/regorus). The 1024-column cap rejects realistic policies
emitted by `genpolicy`: the `NVIDIA_REQUIRE_CUDA` environment variable
on `nvcr.io/nvidia/k8s/cuda-sample` is roughly 1.3 KiB on a single line,
so the agent's `set_policy()` returns an error, the agent (PID 1) exits,
the guest kernel reboots, and the runtime eventually times out
connecting to the agent's vsock.

regorus PR #624 ("feat: make policy length limits configurable per
engine") adds `Engine::set_policy_length_config`, but it has not been
released yet -- the latest published version is still 0.9.1, which
predates that change.

Pin `regorus` to the upstream commit that includes #624 and call the
new setter from `AgentPolicy::new_engine()` with values that comfortably
fit any policy we expect to evaluate (64 KiB per line, 16 MiB per file,
200 000 lines) while still rejecting pathological/minified input. Once
a regorus release > 0.9.1 ships with #624, the dependency can be moved
back to crates.io.

Signed-off-by: Fabiano Fidêncio <ffidencio@nvidia.com>
This commit is contained in:
Fabiano Fidêncio
2026-04-26 10:17:07 +02:00
parent c8fe6a60d0
commit 74d9d043f0
3 changed files with 32 additions and 3 deletions

3
Cargo.lock generated
View File

@@ -5942,8 +5942,7 @@ checksum = "dc897dd8d9e8bd1ed8cdad82b5966c3e0ecae09fb1907d58efaa013543185d0a"
[[package]]
name = "regorus"
version = "0.9.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "656c9768f1d2113590ebc05e2e342a9f76baa97a445f2928f24eec9ae1fb14ac"
source = "git+https://github.com/microsoft/regorus?rev=898643129e3652efd43e596f978d99f85e770235#898643129e3652efd43e596f978d99f85e770235"
dependencies = [
"anyhow",
"data-encoding",

View File

@@ -16,7 +16,18 @@ serde.workspace = true
serde_json.workspace = true
# Agent Policy
regorus = { version = "0.9.1", default-features = false, features = [
#
# Pinned to an upstream commit on `main` instead of a published crate version
# because the 0.9.1 release hard-caps policy lines at 1024 characters and
# files at 1 MiB / 20 000 lines, which rejects realistic policies generated
# by `genpolicy` (e.g. the NVIDIA_REQUIRE_CUDA environment variable on
# `nvcr.io/nvidia/k8s/cuda-sample` images is ~1.3 KiB on a single line).
#
# The pinned commit is microsoft/regorus#624 ("feat: make policy length
# limits configurable per engine"), which adds Engine::set_policy_length_config.
# Switch back to a crates.io version once a release > 0.9.1 containing #624
# is published.
regorus = { git = "https://github.com/microsoft/regorus", rev = "898643129e3652efd43e596f978d99f85e770235", default-features = false, features = [
"arc",
"base64",
"base64url",

View File

@@ -6,13 +6,27 @@
//! Policy evaluation for the kata-agent.
use std::num::{NonZeroU32, NonZeroUsize};
use std::{ffi::OsStr, os::unix::ffi::OsStrExt as _};
use anyhow::{bail, Error, Result};
use protocols::agent::CopyFileRequest;
use regorus::PolicyLengthConfig;
use slog::{debug, error, info, warn};
use tokio::io::AsyncWriteExt;
// Regorus' built-in policy length limits (1024 cols / 1 MiB / 20 000 lines)
// reject realistic policies emitted by `genpolicy`. In particular, container
// `Env` values such as NVIDIA_REQUIRE_CUDA on the upstream NVIDIA CUDA images
// can exceed 1 KiB on a single line. These constants raise the per-engine
// limits to values that comfortably fit any policy we expect to evaluate
// while still rejecting pathological/minified input.
//
// See microsoft/regorus#624 for the upstream API.
const POLICY_MAX_COL: u32 = 64 * 1024; // 64 KiB per line
const POLICY_MAX_FILE_BYTES: usize = 16 * 1024 * 1024; // 16 MiB per file
const POLICY_MAX_LINES: usize = 200_000;
static POLICY_LOG_FILE: &str = "/tmp/policy.jsonl";
static POLICY_DEFAULT_FILE: &str = "/etc/kata-opa/default-policy.rego";
@@ -56,6 +70,11 @@ impl AgentPolicy {
let mut engine = regorus::Engine::new();
engine.set_strict_builtin_errors(false);
engine.set_gather_prints(true);
engine.set_policy_length_config(PolicyLengthConfig {
max_col: NonZeroU32::new(POLICY_MAX_COL).unwrap(),
max_file_bytes: NonZeroUsize::new(POLICY_MAX_FILE_BYTES).unwrap(),
max_lines: NonZeroUsize::new(POLICY_MAX_LINES).unwrap(),
});
// assign a slice of the engine data "pstate" to be used as policy state
engine
.add_data(