mirror of
https://github.com/kata-containers/kata-containers.git
synced 2025-09-20 16:27:52 +00:00
genpolicy: container.exec_commands args validation
Keep track of individual exec args instead of joining them in the policy text. Verifying each arg results in a more precise policy, because some of the args might include space characters. This improved validation applies to commands specified in K8s YAML files using: - livenessProbe - readinessProbe - startupProbe - lifecycle.postStart - lifecycle.preStop Signed-off-by: Dan Mihai <dmihai@microsoft.com>
This commit is contained in:
@@ -1124,15 +1124,12 @@ ExecProcessRequest {
|
|||||||
print("ExecProcessRequest 2: input =", input)
|
print("ExecProcessRequest 2: input =", input)
|
||||||
|
|
||||||
# TODO: match input container ID with its corresponding container.exec_commands.
|
# TODO: match input container ID with its corresponding container.exec_commands.
|
||||||
i_command = concat(" ", input.process.Args)
|
|
||||||
print("ExecProcessRequest 3: i_command =", i_command)
|
|
||||||
|
|
||||||
some container in policy_data.containers
|
some container in policy_data.containers
|
||||||
some p_command in container.exec_commands
|
some p_command in container.exec_commands
|
||||||
print("ExecProcessRequest 2: p_command =", p_command)
|
print("ExecProcessRequest 2: p_command =", p_command)
|
||||||
|
|
||||||
# TODO: should other input data fields be validated as well?
|
# TODO: should other input data fields be validated as well?
|
||||||
p_command == i_command
|
p_command == input.process.Args
|
||||||
|
|
||||||
print("ExecProcessRequest 2: true")
|
print("ExecProcessRequest 2: true")
|
||||||
}
|
}
|
||||||
|
@@ -614,36 +614,36 @@ impl Container {
|
|||||||
(yaml_has_command, yaml_has_args)
|
(yaml_has_command, yaml_has_args)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_exec_commands(&self) -> Vec<String> {
|
pub fn get_exec_commands(&self) -> Vec<Vec<String>> {
|
||||||
let mut commands = Vec::new();
|
let mut commands = Vec::new();
|
||||||
|
|
||||||
if let Some(probe) = &self.livenessProbe {
|
if let Some(probe) = &self.livenessProbe {
|
||||||
if let Some(exec) = &probe.exec {
|
if let Some(exec) = &probe.exec {
|
||||||
commands.push(exec.command.join(" "));
|
commands.push(exec.command.clone());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if let Some(probe) = &self.readinessProbe {
|
if let Some(probe) = &self.readinessProbe {
|
||||||
if let Some(exec) = &probe.exec {
|
if let Some(exec) = &probe.exec {
|
||||||
commands.push(exec.command.join(" "));
|
commands.push(exec.command.clone());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if let Some(probe) = &self.startupProbe {
|
if let Some(probe) = &self.startupProbe {
|
||||||
if let Some(exec) = &probe.exec {
|
if let Some(exec) = &probe.exec {
|
||||||
commands.push(exec.command.join(" "));
|
commands.push(exec.command.clone());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if let Some(lifecycle) = &self.lifecycle {
|
if let Some(lifecycle) = &self.lifecycle {
|
||||||
if let Some(postStart) = &lifecycle.postStart {
|
if let Some(postStart) = &lifecycle.postStart {
|
||||||
if let Some(exec) = &postStart.exec {
|
if let Some(exec) = &postStart.exec {
|
||||||
commands.push(exec.command.join(" "));
|
commands.push(exec.command.clone());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if let Some(preStop) = &lifecycle.preStop {
|
if let Some(preStop) = &lifecycle.preStop {
|
||||||
if let Some(exec) = &preStop.exec {
|
if let Some(exec) = &preStop.exec {
|
||||||
commands.push(exec.command.join(" "));
|
commands.push(exec.command.clone());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -271,7 +271,7 @@ pub struct ContainerPolicy {
|
|||||||
/// Allow list of ommand lines that are allowed to be executed using
|
/// Allow list of ommand lines that are allowed to be executed using
|
||||||
/// ExecProcessRequest. By default, all ExecProcessRequest calls are blocked
|
/// ExecProcessRequest. By default, all ExecProcessRequest calls are blocked
|
||||||
/// by the policy.
|
/// by the policy.
|
||||||
exec_commands: Vec<String>,
|
exec_commands: Vec<Vec<String>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// See Reference / Kubernetes API / Config and Storage Resources / Volume.
|
/// See Reference / Kubernetes API / Config and Storage Resources / Volume.
|
||||||
|
@@ -205,12 +205,8 @@ test_pod_policy_error() {
|
|||||||
pod_exec_allowed_command "${pod_name}" "sh" "-c" "ls -l /"
|
pod_exec_allowed_command "${pod_name}" "sh" "-c" "ls -l /"
|
||||||
pod_exec_allowed_command "${pod_name}" "echo" "startupProbe" "test"
|
pod_exec_allowed_command "${pod_name}" "echo" "startupProbe" "test"
|
||||||
|
|
||||||
# This test should fail but it passes because genpolicy joins the exec args from its
|
|
||||||
# input K8s YAML file and from the command being executed, and compares the joined
|
|
||||||
# command lines instead of comparing each argument.
|
|
||||||
pod_exec_allowed_command "${pod_name}" "echo" "livenessProbe test"
|
|
||||||
|
|
||||||
# Try to execute commands disallowed by the policy.
|
# Try to execute commands disallowed by the policy.
|
||||||
|
pod_exec_blocked_command "${pod_name}" "echo" "livenessProbe test"
|
||||||
pod_exec_blocked_command "${pod_name}" "echo" "livenessProbe" "test2"
|
pod_exec_blocked_command "${pod_name}" "echo" "livenessProbe" "test2"
|
||||||
pod_exec_blocked_command "${pod_name}" "echo" "livenessProbe" "test" "yes"
|
pod_exec_blocked_command "${pod_name}" "echo" "livenessProbe" "test" "yes"
|
||||||
pod_exec_blocked_command "${pod_name}" "echo" "livenessProbe" "test foo"
|
pod_exec_blocked_command "${pod_name}" "echo" "livenessProbe" "test foo"
|
||||||
|
Reference in New Issue
Block a user