Skip to content

Commit

Permalink
remove more cobweb traits
Browse files Browse the repository at this point in the history
  • Loading branch information
squell committed Jan 21, 2025
1 parent 64aa649 commit e654771
Show file tree
Hide file tree
Showing 3 changed files with 45 additions and 58 deletions.
43 changes: 2 additions & 41 deletions src/sudo/mod.rs
Original file line number Diff line number Diff line change
@@ -1,9 +1,8 @@
#![forbid(unsafe_code)]

use crate::common::resolve::CurrentUser;
use crate::common::{Context, Error};
use crate::common::Error;
use crate::log::dev_info;
use crate::sudoers::{Judgement, Sudoers};
use crate::system::interface::UserId;
use crate::system::kernel::kernel_check;
use crate::system::timestamp::RecordScope;
Expand All @@ -15,7 +14,7 @@ pub use cli::SudoAction;
#[cfg(not(test))]
use cli::SudoAction;
use pam::PamAuthenticator;
use pipeline::{Pipeline, PolicyPlugin};
use pipeline::Pipeline;
use std::path::Path;

mod cli;
Expand Down Expand Up @@ -66,43 +65,6 @@ pub(crate) fn candidate_sudoers_file() -> &'static Path {
file
}

#[derive(Default)]
pub(crate) struct SudoersPolicy {}

impl PolicyPlugin for SudoersPolicy {
fn init(&mut self) -> Result<Sudoers, Error> {
let sudoers_path = candidate_sudoers_file();

let (sudoers, syntax_errors) =
Sudoers::open(sudoers_path).map_err(|e| Error::Configuration(format!("{e}")))?;

for crate::sudoers::Error {
source,
location,
message,
} in syntax_errors
{
let path = source.as_deref().unwrap_or(sudoers_path);
diagnostic::diagnostic!("{message}", path @ location);
}

Ok(sudoers)
}

fn judge(&mut self, pre: Sudoers, context: &Context) -> Result<Judgement, Error> {
Ok(pre.check(
&*context.current_user,
&context.hostname,
crate::sudoers::Request {
user: &context.target_user,
group: &context.target_group,
command: &context.command.command,
arguments: &context.command.arguments,
},
))
}
}

fn sudo_process() -> Result<(), Error> {
crate::log::SudoLogger::new("sudo: ").into_global_logger();

Expand All @@ -112,7 +74,6 @@ fn sudo_process() -> Result<(), Error> {
kernel_check()?;

let pipeline = Pipeline {
policy: SudoersPolicy::default(),
authenticator: PamAuthenticator::new_cli(),
};

Expand Down
51 changes: 39 additions & 12 deletions src/sudo/pipeline.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ use std::ffi::{OsStr, OsString};
use std::process::exit;

use super::cli::{SudoRunOptions, SudoValidateOptions};
use super::diagnostic;
use crate::common::context::OptionsForContext;
use crate::common::resolve::{AuthUser, CurrentUser};
use crate::common::{Context, Error};
Expand All @@ -19,26 +20,52 @@ use crate::system::{escape_os_str_lossy, Process};

mod list;

pub trait PolicyPlugin {
fn init(&mut self) -> Result<Sudoers, Error>;
fn judge(&mut self, pre: Sudoers, context: &Context) -> Result<Judgement, Error>;
}

pub trait AuthPlugin {
fn init(&mut self, context: &Context) -> Result<(), Error>;
fn authenticate(&mut self, non_interactive: bool, max_tries: u16) -> Result<(), Error>;
fn pre_exec(&mut self, target_user: &str) -> Result<Vec<(OsString, OsString)>, Error>;
fn cleanup(&mut self);
}

pub struct Pipeline<Policy: PolicyPlugin, Auth: AuthPlugin> {
pub policy: Policy,
pub struct Pipeline<Auth: AuthPlugin> {
pub authenticator: Auth,
}

impl<Policy: PolicyPlugin, Auth: AuthPlugin> Pipeline<Policy, Auth> {
fn read_sudoers() -> Result<Sudoers, Error> {
let sudoers_path = super::candidate_sudoers_file();

let (sudoers, syntax_errors) =
Sudoers::open(sudoers_path).map_err(|e| Error::Configuration(format!("{e}")))?;

for crate::sudoers::Error {
source,
location,
message,
} in syntax_errors
{
let path = source.as_deref().unwrap_or(sudoers_path);
diagnostic::diagnostic!("{message}", path @ location);
}

Ok(sudoers)
}

fn judge(policy: Sudoers, context: &Context) -> Result<Judgement, Error> {
Ok(policy.check(
&*context.current_user,
&context.hostname,
crate::sudoers::Request {
user: &context.target_user,
group: &context.target_group,
command: &context.command.command,
arguments: &context.command.arguments,
},
))
}

impl<Auth: AuthPlugin> Pipeline<Auth> {
pub fn run(mut self, cmd_opts: SudoRunOptions) -> Result<(), Error> {
let pre = self.policy.init()?;
let policy = read_sudoers()?;

let (ctx_opts, pipe_opts) = cmd_opts.into();

Expand All @@ -48,9 +75,9 @@ impl<Policy: PolicyPlugin, Auth: AuthPlugin> Pipeline<Policy, Auth> {
)
}

let mut context = build_context(ctx_opts, &pre)?;
let mut context = build_context(ctx_opts, &policy)?;

let policy = self.policy.judge(pre, &context)?;
let policy = judge(policy, &context)?;

let Authorization::Allowed(auth, controls) = policy.authorization() else {
return Err(Error::Authorization(context.current_user.name.to_string()));
Expand Down Expand Up @@ -111,7 +138,7 @@ impl<Policy: PolicyPlugin, Auth: AuthPlugin> Pipeline<Policy, Auth> {
}

pub fn run_validate(mut self, cmd_opts: SudoValidateOptions) -> Result<(), Error> {
let pre = self.policy.init()?;
let pre = read_sudoers()?;
let mut context = build_context(cmd_opts.into(), &pre)?;

match pre.validate_authorization() {
Expand Down
9 changes: 4 additions & 5 deletions src/sudo/pipeline/list.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,14 @@ use std::{borrow::Cow, ops::ControlFlow, path::Path};

use crate::{
common::{Context, Error},
pam::CLIConverser,
sudo::{cli::SudoListOptions, pam::PamAuthenticator, SudoersPolicy},
sudo::cli::SudoListOptions,
sudoers::{Authorization, ListRequest, Request, Sudoers},
system::{interface::UserId, User},
};

use super::{Pipeline, PolicyPlugin};
use super::Pipeline;

impl Pipeline<SudoersPolicy, PamAuthenticator<CLIConverser>> {
impl<Auth: super::AuthPlugin> Pipeline<Auth> {
pub(in crate::sudo) fn run_list(mut self, cmd_opts: SudoListOptions) -> Result<(), Error> {
let verbose_list_mode = cmd_opts.list.is_verbose();
let other_user = cmd_opts
Expand All @@ -24,7 +23,7 @@ impl Pipeline<SudoersPolicy, PamAuthenticator<CLIConverser>> {

let original_command = cmd_opts.positional_args.first().cloned();

let sudoers = self.policy.init()?;
let sudoers = super::read_sudoers()?;
let mut context = super::build_context(cmd_opts.into(), &sudoers)?;

if original_command.is_some() && !context.command.resolved {
Expand Down

0 comments on commit e654771

Please sign in to comment.