diff --git a/src/agent/src/config.rs b/src/agent/src/config.rs index 3f721afbb9..a83328440c 100644 --- a/src/agent/src/config.rs +++ b/src/agent/src/config.rs @@ -55,6 +55,10 @@ const VSOCK_ADDR: &str = "vsock://-1"; const SERVER_ADDR_ENV_VAR: &str = "KATA_AGENT_SERVER_ADDR"; const LOG_LEVEL_ENV_VAR: &str = "KATA_AGENT_LOG_LEVEL"; const TRACING_ENV_VAR: &str = "KATA_AGENT_TRACING"; +#[cfg(feature = "agent-policy")] +// Policy file environment variable to pass a policy document +// to initialize agent policy engine. +const POLICY_FILE_VAR: &str = "KATA_AGENT_POLICY_FILE"; const ERR_INVALID_LOG_LEVEL: &str = "invalid log level"; const ERR_INVALID_LOG_LEVEL_PARAM: &str = "invalid log level parameter"; @@ -125,6 +129,8 @@ pub struct AgentConfig { pub enable_signature_verification: bool, #[cfg(feature = "guest-pull")] pub image_policy_file: String, + #[cfg(feature = "agent-policy")] + pub policy_file: String, } #[derive(Debug, Deserialize)] @@ -152,6 +158,8 @@ pub struct AgentConfigBuilder { pub enable_signature_verification: Option, #[cfg(feature = "guest-pull")] pub image_policy_file: Option, + #[cfg(feature = "agent-policy")] + pub policy_file: Option, } macro_rules! config_override { @@ -225,6 +233,8 @@ impl Default for AgentConfig { enable_signature_verification: false, #[cfg(feature = "guest-pull")] image_policy_file: String::from(""), + #[cfg(feature = "agent-policy")] + policy_file: String::from(""), } } } @@ -275,6 +285,8 @@ impl FromStr for AgentConfig { } config_override!(agent_config_builder, agent_config, secure_storage_integrity); + #[cfg(feature = "agent-policy")] + config_override!(agent_config_builder, agent_config, policy_file); Ok(agent_config) } } @@ -456,6 +468,11 @@ impl AgentConfig { self.tracing = get_bool_value(&name_value).unwrap_or(false); } + + #[cfg(feature = "agent-policy")] + if let Ok(policy_file) = env::var(POLICY_FILE_VAR) { + self.policy_file = policy_file; + } } } @@ -662,6 +679,8 @@ mod tests { enable_signature_verification: bool, #[cfg(feature = "guest-pull")] image_policy_file: &'a str, + #[cfg(feature = "agent-policy")] + policy_file: &'a str, } impl Default for TestData<'_> { @@ -688,6 +707,8 @@ mod tests { enable_signature_verification: false, #[cfg(feature = "guest-pull")] image_policy_file: "", + #[cfg(feature = "agent-policy")] + policy_file: "", } } } @@ -1174,6 +1195,14 @@ mod tests { image_policy_file: "file:///etc/image-policy.json", ..Default::default() }, + #[cfg(feature = "agent-policy")] + // Test environment + TestData { + contents: "", + env_vars: vec!["KATA_AGENT_POLICY_FILE=/tmp/policy.rego"], + policy_file: "/tmp/policy.rego", + ..Default::default() + }, ]; let dir = tempdir().expect("failed to create tmpdir"); @@ -1248,6 +1277,9 @@ mod tests { "{}", msg ); + #[cfg(feature = "agent-policy")] + assert_eq!(d.policy_file, config.policy_file, "{}", msg); + for v in vars_to_unset { env::remove_var(v); } diff --git a/src/agent/src/main.rs b/src/agent/src/main.rs index 3b45b2d467..88a5ec01a5 100644 --- a/src/agent/src/main.rs +++ b/src/agent/src/main.rs @@ -600,11 +600,7 @@ fn init_agent_as_init(logger: &Logger, unified_cgroup_hierarchy: bool) -> Result #[cfg(feature = "agent-policy")] async fn initialize_policy() -> Result<()> { - AGENT_POLICY - .lock() - .await - .initialize("/etc/kata-opa/default-policy.rego") - .await + AGENT_POLICY.lock().await.initialize().await } // The Rust standard library had suppressed the default SIGPIPE behavior, diff --git a/src/agent/src/policy.rs b/src/agent/src/policy.rs index d9ddba46dd..ccac317d0f 100644 --- a/src/agent/src/policy.rs +++ b/src/agent/src/policy.rs @@ -11,6 +11,7 @@ use crate::rpc::ttrpc_error; use crate::{AGENT_CONFIG, AGENT_POLICY}; static POLICY_LOG_FILE: &str = "/tmp/policy.txt"; +static POLICY_DEFAULT_FILE: &str = "/etc/kata-opa/default-policy.rego"; /// Convenience macro to obtain the scope logger macro_rules! sl { @@ -85,7 +86,7 @@ impl AgentPolicy { } /// Initialize regorus. - pub async fn initialize(&mut self, default_policy_file: &str) -> Result<()> { + pub async fn initialize(&mut self) -> Result<()> { if AGENT_CONFIG.log_level.as_usize() >= slog::Level::Debug.as_usize() { self.log_file = Some( tokio::fs::OpenOptions::new() @@ -98,6 +99,14 @@ impl AgentPolicy { debug!(sl!(), "policy: log file: {}", POLICY_LOG_FILE); } + // Check if policy file has been set via AgentConfig + // If empty, use default file. + let mut default_policy_file = AGENT_CONFIG.policy_file.clone(); + if default_policy_file.is_empty() { + default_policy_file = POLICY_DEFAULT_FILE.to_string(); + } + info!(sl!(), "default policy: {default_policy_file}"); + self.engine.add_policy_from_file(default_policy_file)?; self.update_allow_failures_flag().await?; Ok(()) diff --git a/tests/functional/kata-agent-apis/setup_common.sh b/tests/functional/kata-agent-apis/setup_common.sh index 1c60409508..bc8d091a8a 100755 --- a/tests/functional/kata-agent-apis/setup_common.sh +++ b/tests/functional/kata-agent-apis/setup_common.sh @@ -33,7 +33,6 @@ agent_log_level="debug" keep_logs=false local_policy_file="/opt/kata/test.rego" -policy_file="/etc/kata-opa/default-policy.rego" cleanup() { @@ -43,9 +42,7 @@ cleanup() stop_agent - sudo unlink $policy_file sudo rm $local_policy_file - sudo rm -rf $(dirname ${policy_file}) local sandbox_dir="/run/sandbox-ns/" sudo umount -f "${sandbox_dir}/uts" "${sandbox_dir}/ipc" &>/dev/null || true @@ -166,6 +163,7 @@ start_agent() RUST_BACKTRACE=full \ KATA_AGENT_LOG_LEVEL=${agent_log_level} \ KATA_AGENT_SERVER_ADDR=${local_agent_server_addr} \ + KATA_AGENT_POLICY_FILE=${local_policy_file} \ ${agent_binary} \ &> ${log_file} \ & @@ -191,12 +189,7 @@ install_policy_doc() allow_all_rego_file="${repo_root_dir}/src/kata-opa/allow-all.rego" [ ! -f $allow_all_rego_file ] && die "Failed to locate allow-all.rego file" - local policy_dir=$(dirname ${policy_file}) - [ ! -d $policy_dir ] && sudo mkdir -p $policy_dir || true - sudo cp $allow_all_rego_file $local_policy_file - - [ ! -f $policy_file ] && sudo ln -s $local_policy_file $policy_file || die "Failed to setup local policy file, exists: $policy_file" } # Same reason as above, we do not have the necessary components to start the coco processes