From: Ian Jackson Date: Tue, 20 Oct 2020 21:19:09 +0000 (+0100) Subject: wip new account etc. X-Git-Tag: otter-0.2.0~613 X-Git-Url: https://www.chiark.greenend.org.uk/ucgi/~ianmdlvl/git?a=commitdiff_plain;h=ad1bc3e65bedc51631a76f8262d7f2f8a3b66eb4;p=otter.git wip new account etc. Signed-off-by: Ian Jackson --- diff --git a/src/accounts.rs b/src/accounts.rs index 05416f23..0676f5e5 100644 --- a/src/accounts.rs +++ b/src/accounts.rs @@ -140,7 +140,7 @@ pub mod loaded_acl { use crate::imports::*; pub trait Perm : FromPrimitive + ToPrimitive - + Copy + Eq + Hash + Sync + Send { } + + Copy + Eq + Hash + Sync + Send + 'static { } #[derive(Copy,Clone,Debug)] pub struct PermSet (u64, PhantomData<&'static P>); @@ -157,8 +157,8 @@ pub mod loaded_acl { #[derive(Debug,Clone)] struct LoadedAclEntry { pat: glob::Pattern, - allow: Bitmap, - deny: Bitmap, + allow: PermSet

, + deny: PermSet

, ptype: PhantomData<&'static P>, } @@ -170,14 +170,15 @@ pub mod loaded_acl { ptype: PhantomData<&'static P>, } - impl LoadedAcl

{ - fn entries(&'s self) -> impl Iterator> { - self.owner_account.map( + impl<'e, P:Perm> EffectiveAcl<'e, P> { + fn entries(&self) -> impl Iterator> { + self.owner_account.iter().map( |owner| - AclEntryRef { pat: Left(owner), allow: !0, deny: 0, ptype } - ).chain(self.entries.map( - |LoadedAclEntry { pat, allow, deny }| - AclEntryRef { pat: Left(pat), allow: allow.0, deny: deny.0 } + AclEntryRef { pat: Left(owner), allow: !0, deny: 0, + ptype: PhantomData } + ).chain(self.acl.0.iter().map( + |&LoadedAclEntry { ref pat, ref allow, ref deny, ptype }| + AclEntryRef { pat: Right(pat), allow: allow.0, deny: deny.0, ptype } )) } @@ -194,17 +195,19 @@ pub mod loaded_acl { needed &= !allow; if needed == 0 { return Ok(()) } } - Err(ME::PermissionDenied) + Err(MgmtError::PermissionDenied) } } - impl From for PermSet

where I: IntoIterator { + impl<'i, P:Perm, I> From for PermSet

+ where I: IntoIterator + { fn from(i: I) -> Self { i.into_iter().fold(0, |b, i| b | i.to_u64().unwrap()) } } - fn unpack(unpacked: Bitmap) -> HashSet

{ + fn unpack(unpacked: PermSet

) -> HashSet

{ let mut s = HashSet::new(); for n in 0.. { let v = match FromPrimitive::from_u64(n) { Some(v) => v, None => break }; diff --git a/src/cmdlistener.rs b/src/cmdlistener.rs index 190ee91e..0f1075d8 100644 --- a/src/cmdlistener.rs +++ b/src/cmdlistener.rs @@ -157,7 +157,7 @@ fn execute_game_insn(cs: &CommandStream, fn readonly ExecuteGameInsnResults>( cs: &CommandStream, - ig: &Unauthorised, + ig: &Unauthorised, p: PermSet, f: F) -> ExecuteGameInsnResults { @@ -571,6 +571,16 @@ impl CommandStream<'_> { } } +#[throws(MgmtError)] +fn authorise_by_account(cs: &CommandStream, wanted: &AccountScope) + -> Authorisation { + let currently = &cs.account.as_ref()?.account; + if currently == wanted { + return Authorisation::authorised(currently); + } + throw!(MgmtError::AuthorisationError) +} + #[throws(MgmtError)] fn authorise_scope_direct(cs: &CommandStream, wanted: &AccountScope) -> Authorisation { diff --git a/src/global.rs b/src/global.rs index b597e0b2..b24c748a 100644 --- a/src/global.rs +++ b/src/global.rs @@ -254,7 +254,7 @@ impl InstanceRef { impl Unauthorised, A> { #[throws(MgmtError)] - pub fn check_acl(&mut self, p: PermSet) + pub fn check_acl(&mut self, p: PermSet) -> &mut InstanceGuard { let auth = { let acl = self.by(Authorisation::authorise_any()).acl; diff --git a/src/imports.rs b/src/imports.rs index 9c187611..e5e1093b 100644 --- a/src/imports.rs +++ b/src/imports.rs @@ -105,6 +105,8 @@ pub use serde_with::serde_as; pub use ordered_float::OrderedFloat; +pub use either::{Either,Left,Right}; + pub use crate::global::*; pub use crate::gamestate::*; pub use crate::pieces::*; @@ -123,7 +125,7 @@ pub use crate::debugreader::DebugReader; pub use crate::shapelib; pub use crate::tz::*; pub use crate::accounts::*; -pub use crate::accounts::loaded_acl::{self,LoadedAcl}; +pub use crate::accounts::loaded_acl::{self,LoadedAcl,PermSet}; pub use zcoord::{self, ZCoord}; diff --git a/src/spec.rs b/src/spec.rs index 44772e85..dd975760 100644 --- a/src/spec.rs +++ b/src/spec.rs @@ -14,6 +14,7 @@ use thiserror::Error; use crate::error::display_as_debug; use crate::accounts::AccountName; use std::hash::Hash; +use num_derive::{ToPrimitive, FromPrimitive}; pub use implementation::PlayerAccessSpec; @@ -74,7 +75,8 @@ pub struct AclEntry { #[derive(Debug,Clone,Copy,Serialize,Deserialize)] #[derive(Hash,Eq,PartialEq,Ord,PartialOrd)] -enum TablePermission { +#[derive(FromPrimitive,ToPrimitive)] +pub enum TablePermission { AddPlayer, ChangePieces, RemovePlayer, @@ -223,6 +225,8 @@ pub mod implementation { use crate::imports::*; type Insn = crate::commands::MgmtGameInstruction; + impl loaded_acl::Perm for TablePermission { } + type TDE = TokenDeliveryError; pub fn raw_token_debug_as_str(s: &str, f: &mut fmt::Formatter)