use crate::error::{PqcError, Result};
use core::sync::atomic::{AtomicU8, Ordering};
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub enum Role {
User,
CryptoOfficer,
}
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
enum AuthState {
LoggedOut = 0,
LoggedInUser = 1,
LoggedInCO = 2,
}
static AUTH_STATE: AtomicU8 = AtomicU8::new(AuthState::LoggedOut as u8);
pub fn login(role: Role, password: &[u8]) -> Result<()> {
let user_pw = b"user123";
let co_pw = b"admin456";
match role {
Role::User => {
if password == user_pw {
AUTH_STATE.store(AuthState::LoggedInUser as u8, Ordering::Release);
Ok(())
} else {
Err(PqcError::AuthenticationFailure)
}
}
Role::CryptoOfficer => {
if password == co_pw {
AUTH_STATE.store(AuthState::LoggedInCO as u8, Ordering::Release);
Ok(())
} else {
Err(PqcError::AuthenticationFailure)
}
}
}
}
pub fn logout() {
AUTH_STATE.store(AuthState::LoggedOut as u8, Ordering::Release);
}
pub fn check_authority(required_role: Role) -> Result<()> {
let current = AUTH_STATE.load(Ordering::Acquire);
match (required_role, current) {
(Role::User, 1) => Ok(()), (Role::CryptoOfficer, 2) => Ok(()), _ => Err(PqcError::AuthenticationFailure),
}
}
pub fn is_authenticated() -> bool {
AUTH_STATE.load(Ordering::Acquire) != AuthState::LoggedOut as u8
}