use crate::rand;
use crate::server::ProducesTickets;
use crate::Error;

use ring::aead;
use std::mem;
use std::sync::{Arc, Mutex, MutexGuard};
use std::time;

/// The timebase for expiring and rolling tickets and ticketing
/// keys.  This is UNIX wall time in seconds.
///
/// This is guaranteed to be on or after the UNIX epoch.
#[derive(Clone, Copy, Debug)]
pub struct TimeBase(time::Duration);

impl TimeBase {
    #[inline]
    pub fn now() -> Result<Self, time::SystemTimeError> {
        Ok(Self(
            time::SystemTime::now().duration_since(time::UNIX_EPOCH)?,
        ))
    }

    #[inline]
    pub fn as_secs(&self) -> u64 {
        self.0.as_secs()
    }
}

/// This is a `ProducesTickets` implementation which uses
/// any *ring* `aead::Algorithm` to encrypt and authentication
/// the ticket payload.  It does not enforce any lifetime
/// constraint.
struct AeadTicketer {
    alg: &'static aead::Algorithm,
    key: aead::LessSafeKey,
    lifetime: u32,
}

impl AeadTicketer {
    /// Make a ticketer with recommended configuration and a random key.
    fn new() -> Result<Self, rand::GetRandomFailed> {
        let mut key = [0u8; 32];
        rand::fill_random(&mut key)?;

        let alg = &aead::CHACHA20_POLY1305;
        let key = aead::UnboundKey::new(alg, &key).unwrap();

        Ok(Self {
            alg,
            key: aead::LessSafeKey::new(key),
            lifetime: 60 * 60 * 12,
        })
    }
}

impl ProducesTickets for AeadTicketer {
    fn enabled(&self) -> bool {
        true
    }
    fn lifetime(&self) -> u32 {
        self.lifetime
    }

    /// Encrypt `message` and return the ciphertext.
    fn encrypt(&self, message: &[u8]) -> Option<Vec<u8>> {
        // Random nonce, because a counter is a privacy leak.
        let mut nonce_buf = [0u8; 12];
        rand::fill_random(&mut nonce_buf).ok()?;
        let nonce = ring::aead::Nonce::assume_unique_for_key(nonce_buf);
        let aad = ring::aead::Aad::empty();

        let mut ciphertext =
            Vec::with_capacity(nonce_buf.len() + message.len() + self.key.algorithm().tag_len());
        ciphertext.extend(nonce_buf);
        ciphertext.extend(message);
        self.key
            .seal_in_place_separate_tag(nonce, aad, &mut ciphertext[nonce_buf.len()..])
            .map(|tag| {
                ciphertext.extend(tag.as_ref());
                ciphertext
            })
            .ok()
    }

    /// Decrypt `ciphertext` and recover the original message.
    fn decrypt(&self, ciphertext: &[u8]) -> Option<Vec<u8>> {
        // Non-panicking `let (nonce, ciphertext) = ciphertext.split_at(...)`.
        let nonce = ciphertext.get(..self.alg.nonce_len())?;
        let ciphertext = ciphertext.get(nonce.len()..)?;

        // This won't fail since `nonce` has the required length.
        let nonce = ring::aead::Nonce::try_assume_unique_for_key(nonce).ok()?;

        let mut out = Vec::from(ciphertext);

        let plain_len = self
            .key
            .open_in_place(nonce, aead::Aad::empty(), &mut out)
            .ok()?
            .len();
        out.truncate(plain_len);

        Some(out)
    }
}

struct TicketSwitcherState {
    next: Option<Box<dyn ProducesTickets>>,
    current: Box<dyn ProducesTickets>,
    previous: Option<Box<dyn ProducesTickets>>,
    next_switch_time: u64,
}

/// A ticketer that has a 'current' sub-ticketer and a single
/// 'previous' ticketer.  It creates a new ticketer every so
/// often, demoting the current ticketer.
struct TicketSwitcher {
    generator: fn() -> Result<Box<dyn ProducesTickets>, rand::GetRandomFailed>,
    lifetime: u32,
    state: Mutex<TicketSwitcherState>,
}

impl TicketSwitcher {
    /// `lifetime` is in seconds, and is how long the current ticketer
    /// is used to generate new tickets.  Tickets are accepted for no
    /// longer than twice this duration.  `generator` produces a new
    /// `ProducesTickets` implementation.
    fn new(
        lifetime: u32,
        generator: fn() -> Result<Box<dyn ProducesTickets>, rand::GetRandomFailed>,
    ) -> Result<Self, Error> {
        let now = TimeBase::now()?;
        Ok(Self {
            generator,
            lifetime,
            state: Mutex::new(TicketSwitcherState {
                next: Some(generator()?),
                current: generator()?,
                previous: None,
                next_switch_time: now
                    .as_secs()
                    .saturating_add(u64::from(lifetime)),
            }),
        })
    }

    /// If it's time, demote the `current` ticketer to `previous` (so it
    /// does no new encryptions but can do decryption) and use next for a
    /// new `current` ticketer.
    ///
    /// Calling this regularly will ensure timely key erasure.  Otherwise,
    /// key erasure will be delayed until the next encrypt/decrypt call.
    ///
    /// For efficiency, this is also responsible for locking the state mutex
    /// and returning the mutexguard.
    fn maybe_roll(&self, now: TimeBase) -> Option<MutexGuard<TicketSwitcherState>> {
        // The code below aims to make switching as efficient as possible
        // in the common case that the generator never fails. To achieve this
        // we run the following steps:
        //  1. If no switch is necessary, just return the mutexguard
        //  2. Shift over all of the ticketers (so current becomes previous,
        //     and next becomes current). After this, other threads can
        //     start using the new current ticketer.
        //  3. unlock mutex and generate new ticketer.
        //  4. Place new ticketer in next and return current
        //
        // There are a few things to note here. First, we don't check whether
        // a new switch might be needed in step 4, even though, due to locking
        // and entropy collection, significant amounts of time may have passed.
        // This is to guarantee that the thread doing the switch will eventually
        // make progress.
        //
        // Second, because next may be None, step 2 can fail. In that case
        // we enter a recovery mode where we generate 2 new ticketers, one for
        // next and one for the current ticketer. We then take the mutex a
        // second time and redo the time check to see if a switch is still
        // necessary.
        //
        // This somewhat convoluted approach ensures good availability of the
        // mutex, by ensuring that the state is usable and the mutex not held
        // during generation. It also ensures that, so long as the inner
        // ticketer never generates panics during encryption/decryption,
        // we are guaranteed to never panic when holding the mutex.

        let now = now.as_secs();
        let mut are_recovering = false; // Are we recovering from previous failure?
        {
            // Scope the mutex so we only take it for as long as needed
            let mut state = self.state.lock().ok()?;

            // Fast path in case we do not need to switch to the next ticketer yet
            if now <= state.next_switch_time {
                return Some(state);
            }

            // Make the switch, or mark for recovery if not possible
            if let Some(next) = state.next.take() {
                state.previous = Some(mem::replace(&mut state.current, next));
                state.next_switch_time = now.saturating_add(u64::from(self.lifetime));
            } else {
                are_recovering = true;
            }
        }

        // We always need a next, so generate it now
        let next = (self.generator)().ok()?;
        if !are_recovering {
            // Normal path, generate new next and place it in the state
            let mut state = self.state.lock().ok()?;
            state.next = Some(next);
            Some(state)
        } else {
            // Recovering, generate also a new current ticketer, and modify state
            // as needed. (we need to redo the time check, otherwise this might
            // result in very rapid switching of ticketers)
            let new_current = (self.generator)().ok()?;
            let mut state = self.state.lock().ok()?;
            state.next = Some(next);
            if now > state.next_switch_time {
                state.previous = Some(mem::replace(&mut state.current, new_current));
                state.next_switch_time = now.saturating_add(u64::from(self.lifetime));
            }
            Some(state)
        }
    }
}

impl ProducesTickets for TicketSwitcher {
    fn lifetime(&self) -> u32 {
        self.lifetime * 2
    }

    fn enabled(&self) -> bool {
        true
    }

    fn encrypt(&self, message: &[u8]) -> Option<Vec<u8>> {
        let state = self.maybe_roll(TimeBase::now().ok()?)?;

        state.current.encrypt(message)
    }

    fn decrypt(&self, ciphertext: &[u8]) -> Option<Vec<u8>> {
        let state = self.maybe_roll(TimeBase::now().ok()?)?;

        // Decrypt with the current key; if that fails, try with the previous.
        state
            .current
            .decrypt(ciphertext)
            .or_else(|| {
                state
                    .previous
                    .as_ref()
                    .and_then(|previous| previous.decrypt(ciphertext))
            })
    }
}

/// A concrete, safe ticket creation mechanism.
pub struct Ticketer {}

fn generate_inner() -> Result<Box<dyn ProducesTickets>, rand::GetRandomFailed> {
    Ok(Box::new(AeadTicketer::new()?))
}

impl Ticketer {
    /// Make the recommended Ticketer.  This produces tickets
    /// with a 12 hour life and randomly generated keys.
    ///
    /// The encryption mechanism used in Chacha20Poly1305.
    pub fn new() -> Result<Arc<dyn ProducesTickets>, Error> {
        Ok(Arc::new(TicketSwitcher::new(6 * 60 * 60, generate_inner)?))
    }
}

#[test]
fn basic_pairwise_test() {
    let t = Ticketer::new().unwrap();
    assert!(t.enabled());
    let cipher = t.encrypt(b"hello world").unwrap();
    let plain = t.decrypt(&cipher).unwrap();
    assert_eq!(plain, b"hello world");
}

#[test]
fn ticketswitcher_switching_test() {
    let t = Arc::new(TicketSwitcher::new(1, generate_inner).unwrap());
    let now = TimeBase::now().unwrap();
    let cipher1 = t.encrypt(b"ticket 1").unwrap();
    assert_eq!(t.decrypt(&cipher1).unwrap(), b"ticket 1");
    {
        // Trigger new ticketer
        t.maybe_roll(TimeBase(now.0 + std::time::Duration::from_secs(10)));
    }
    let cipher2 = t.encrypt(b"ticket 2").unwrap();
    assert_eq!(t.decrypt(&cipher1).unwrap(), b"ticket 1");
    assert_eq!(t.decrypt(&cipher2).unwrap(), b"ticket 2");
    {
        // Trigger new ticketer
        t.maybe_roll(TimeBase(now.0 + std::time::Duration::from_secs(20)));
    }
    let cipher3 = t.encrypt(b"ticket 3").unwrap();
    assert!(t.decrypt(&cipher1).is_none());
    assert_eq!(t.decrypt(&cipher2).unwrap(), b"ticket 2");
    assert_eq!(t.decrypt(&cipher3).unwrap(), b"ticket 3");
}

#[cfg(test)]
fn fail_generator() -> Result<Box<dyn ProducesTickets>, rand::GetRandomFailed> {
    Err(rand::GetRandomFailed)
}

#[test]
fn ticketswitcher_recover_test() {
    let mut t = TicketSwitcher::new(1, generate_inner).unwrap();
    let now = TimeBase::now().unwrap();
    let cipher1 = t.encrypt(b"ticket 1").unwrap();
    assert_eq!(t.decrypt(&cipher1).unwrap(), b"ticket 1");
    t.generator = fail_generator;
    {
        // Failed new ticketer
        t.maybe_roll(TimeBase(now.0 + std::time::Duration::from_secs(10)));
    }
    t.generator = generate_inner;
    let cipher2 = t.encrypt(b"ticket 2").unwrap();
    assert_eq!(t.decrypt(&cipher1).unwrap(), b"ticket 1");
    assert_eq!(t.decrypt(&cipher2).unwrap(), b"ticket 2");
    {
        // recover
        t.maybe_roll(TimeBase(now.0 + std::time::Duration::from_secs(20)));
    }
    let cipher3 = t.encrypt(b"ticket 3").unwrap();
    assert!(t.decrypt(&cipher1).is_none());
    assert_eq!(t.decrypt(&cipher2).unwrap(), b"ticket 2");
    assert_eq!(t.decrypt(&cipher3).unwrap(), b"ticket 3");
}
