Docs: Add documentation comments
This commit is contained in:
parent
c08ad88303
commit
392d0ca315
|
@ -1,9 +1,12 @@
|
|||
[package]
|
||||
name = "false-bottom"
|
||||
version = "0.1.0"
|
||||
description = "A deniable encryption scheme"
|
||||
repository = "https://codeberg.org/skran/false-bottom"
|
||||
author = ["K Shiva Kiran <shiva_kr@riseup.net>"]
|
||||
license = "GPL-3.0-or-later"
|
||||
edition = "2021"
|
||||
|
||||
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
|
||||
|
||||
[dependencies]
|
||||
rand = "0.8.5"
|
||||
|
@ -11,3 +14,6 @@ crypto-bigint = {version = "0.5.5", features = ["generic-array"]}
|
|||
base64 = "0.21.7"
|
||||
bincode = "1.3.3"
|
||||
typenum = "1.17.0"
|
||||
|
||||
[lib]
|
||||
doctest = false
|
17
src/algo.rs
17
src/algo.rs
|
@ -9,21 +9,27 @@ where
|
|||
{
|
||||
const MODULUS: NonZero<T>;
|
||||
|
||||
fn init(n: usize, k: usize) -> Result<FBObj<T>, FBError> {
|
||||
if n < k || k < 2 {
|
||||
/// Creates a new [`FBObj`].
|
||||
/// The keybase and ciphertext are initialized from random values.
|
||||
/// Bounds: `2 <= keybase_len <= cipher_len`
|
||||
/// # Errors
|
||||
/// [InvalidParams](FBError::InvalidParams)
|
||||
fn init(cipher_len: usize, keybase_len: usize) -> Result<FBObj<T>, FBError> {
|
||||
if cipher_len < keybase_len || keybase_len < 2 {
|
||||
return Err(FBError::InvalidParams);
|
||||
}
|
||||
let mut rng = rand::thread_rng();
|
||||
let r = (0..k)
|
||||
let r = (0..keybase_len)
|
||||
.map(|_| T::random_mod(&mut rng, &Self::MODULUS))
|
||||
.collect();
|
||||
let c = (0..n)
|
||||
let c = (0..cipher_len)
|
||||
.map(|_| T::random_mod(&mut rng, &Self::MODULUS))
|
||||
.collect();
|
||||
|
||||
Ok(FBObj { c, r })
|
||||
}
|
||||
|
||||
/// Adds the provided message to the ciphertext.
|
||||
fn add(&mut self, msg: &[u8]) -> FBKey {
|
||||
let indices = T::pack(msg)
|
||||
.into_iter()
|
||||
|
@ -33,6 +39,9 @@ where
|
|||
FBKey { indices }
|
||||
}
|
||||
|
||||
/// Decrypts the message that corresponds to the provided key.
|
||||
/// # Errors
|
||||
/// [InvalidKey](FBError::InvalidKey)
|
||||
fn decrypt(&self, key: &FBKey) -> Result<Vec<u8>, FBError> {
|
||||
let decr = key.indices
|
||||
.iter()
|
||||
|
|
|
@ -7,6 +7,7 @@ where
|
|||
Self: FBObjTrait<T>,
|
||||
T: ArrayEncoding + Bounded,
|
||||
{
|
||||
/// Returns the byte representation of the ciphertext and keybase.
|
||||
fn to_bytes(&self) -> (Vec<u8>, Vec<u8>) {
|
||||
let c = self.cipher().iter()
|
||||
.flat_map(|bigint| bigint.to_le_byte_array())
|
||||
|
@ -18,12 +19,17 @@ where
|
|||
(c, r)
|
||||
}
|
||||
|
||||
/// Returns the base64 encoded representation of the ciphertext and keybase.
|
||||
fn export(&self) -> (String, String) {
|
||||
let (c, r) = self.to_bytes();
|
||||
|
||||
(BASE64_STANDARD.encode(c), BASE64_STANDARD.encode(r))
|
||||
}
|
||||
|
||||
/// Constructs the [`FBObj`] from the provided byte representations of
|
||||
/// ciphertext and keybase.
|
||||
/// # Errors
|
||||
/// - [InvalidParams](FBError::InvalidParams) - Are the parameters in the wrong order?
|
||||
fn from_bytes(cipher: &[u8], keybase: &[u8]) -> Result<FBObj<T>, FBError> {
|
||||
let chunk_to_uint = |chunk| {
|
||||
T::from_le_byte_array(
|
||||
|
@ -42,6 +48,11 @@ where
|
|||
Ok(FBObj {c, r})
|
||||
}
|
||||
|
||||
/// Constructs the [`FBObj`] from the provided base64 encoded forms of
|
||||
/// ciphertext and keybase.
|
||||
/// # Errors
|
||||
/// - [DecodeError](FBError::DecodeError)
|
||||
/// - [InvalidParams](FBError::InvalidParams) - Are the parameters in the wrong order?
|
||||
fn import(cipher: &str, keybase: &str) -> Result<FBObj<T>, FBError> {
|
||||
let c_bytes = BASE64_STANDARD.decode(cipher)
|
||||
.map_err(|_| FBError::DecodeError)?;
|
||||
|
|
|
@ -2,8 +2,12 @@ use std::fmt;
|
|||
|
||||
#[derive(Debug)]
|
||||
pub enum FBError {
|
||||
/// Unable to decode the given data.
|
||||
DecodeError,
|
||||
/// The provided key is invalid w.r.t this False Bottom Object.
|
||||
InvalidKey,
|
||||
/// Keybase length (k) or Cipher length (n) out of bounds.
|
||||
/// Valid bounds: (2 <= k <= n).
|
||||
InvalidParams,
|
||||
}
|
||||
|
||||
|
|
|
@ -2,22 +2,28 @@ use crate::FBError;
|
|||
use base64::prelude::{BASE64_STANDARD, Engine};
|
||||
use bincode::{Options, DefaultOptions};
|
||||
|
||||
/// A key object that is specific to a message.
|
||||
pub struct FBKey {
|
||||
pub(crate) indices: Vec<Vec<(usize, usize)>>,
|
||||
}
|
||||
|
||||
impl FBKey {
|
||||
|
||||
/// Returns the byte representation of the key.
|
||||
pub fn to_bytes(&self) -> Vec<u8> {
|
||||
let binc = DefaultOptions::new();
|
||||
binc.serialize(&self.indices)
|
||||
.expect("Should be fine")
|
||||
}
|
||||
|
||||
/// Returns the base64 encoded representation of the key.
|
||||
pub fn export(&self) -> String {
|
||||
BASE64_STANDARD.encode(&self.to_bytes())
|
||||
}
|
||||
|
||||
/// Constructs the key from the provided bytes.
|
||||
/// # Errors
|
||||
/// [DecodeError](FBError::DecodeError)
|
||||
pub fn from_bytes(fbkey: &[u8]) -> Result<FBKey, FBError> {
|
||||
let binc = DefaultOptions::new();
|
||||
let indices: Vec<_> = binc.deserialize(&fbkey)
|
||||
|
@ -29,6 +35,9 @@ impl FBKey {
|
|||
Ok (FBKey {indices})
|
||||
}
|
||||
|
||||
/// Constructs the key from the provided base64 encoded form.
|
||||
/// # Errors
|
||||
/// [DecodeError](FBError::DecodeError)
|
||||
pub fn import(key_str: &str) -> Result<FBKey, FBError> {
|
||||
let indice_bytes = BASE64_STANDARD.decode(key_str)
|
||||
.map_err(|_| FBError::DecodeError)?;
|
||||
|
|
|
@ -3,6 +3,7 @@ pub mod fb128;
|
|||
use crate::{BlockOps, Encode, FieldOps};
|
||||
use crypto_bigint::{ArrayEncoding, Bounded, RandomMod};
|
||||
|
||||
/// The False Bottom Object holds the ciphertext and the keybase. The provided type aliases can be used to pick a block size.
|
||||
pub struct FBObj<T> {
|
||||
pub(crate) c: Vec<T>,
|
||||
pub(crate) r: Vec<T>,
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
use crate::{FBAlgo, FBObj, FieldOps, Packing, WrappingOps};
|
||||
use crypto_bigint::{Limb, NonZero, U128};
|
||||
|
||||
/// [`FBObj`] with a block size of 128 bits.
|
||||
pub type FB128 = FBObj<U128>;
|
||||
|
||||
const PRIME_POS_VAL: u16 = 159;
|
||||
|
|
42
src/lib.rs
42
src/lib.rs
|
@ -1,3 +1,42 @@
|
|||
//! ## Usage
|
||||
//! Unlike traditional encryption algorithms that output ciphertext to a given plaintext,
|
||||
//! False Bottom works by "adding" messages to an existing ciphertext.
|
||||
//! As such, the initial ciphertext and the keybase are generated from random data.
|
||||
//! The ciphertext then grows as messages are added whereas the keybase is fixed
|
||||
//! after initialization and is used to generate the keys for the ciphertext.
|
||||
//! The parameters for the [`init()`](FBObj::init()) function determine the size
|
||||
//! (in number of blocks) of the initial ciphertext and keybase respectively.
|
||||
//! Type aliases over [`FBObj`] are provided to pick a block size.
|
||||
//! Ex: [`FB128`] corresponds to a block size of 128 bits.
|
||||
//!
|
||||
//! ### Cipher Initialization:
|
||||
//! ```rust
|
||||
//! use false_bottom::{FB128, FBAlgo};
|
||||
//! // 15 blocks of ciphertext and 12 blocks of keybase with a block size of 128 bits.
|
||||
//! let fb = FB128::init(15, 12);
|
||||
//! ```
|
||||
//!
|
||||
//! ### Adding Messages:
|
||||
//! Messages can be added using the [`add()`](FBObj::add()) method.
|
||||
//! This method returns an object [`FBKey`] that represents the corresponding key for this message.
|
||||
//! This key can only be used to decrypt this message.
|
||||
//! ```rust
|
||||
//! let msg = b"Hello World!";
|
||||
//! let key = fb.add(&msg);
|
||||
//! ```
|
||||
//!
|
||||
//! ### Decryption:
|
||||
//! The [`decrypt()`](FBObj::decrypt()) method returns the message that corresponds
|
||||
//! to the provided [`FBKey`].
|
||||
//! ```rust
|
||||
//! let decrypted = fb.decrypt(&key);
|
||||
//! ```
|
||||
//! There is also an example [here](examples/encryption.rs).
|
||||
//!
|
||||
//! ### Import and Export
|
||||
//! Available formats: Raw bytes and Base64 encoded.
|
||||
//! Refer to the [example](examples/export.rs).
|
||||
|
||||
mod algo;
|
||||
mod arithmetic;
|
||||
mod encoding;
|
||||
|
@ -9,6 +48,7 @@ mod packing;
|
|||
pub use crate::{
|
||||
errors::FBError,
|
||||
fbobj::{
|
||||
FBObj,
|
||||
fb128::FB128,
|
||||
},
|
||||
algo::FBAlgo,
|
||||
|
@ -19,6 +59,6 @@ pub use crate::{
|
|||
use crate::{
|
||||
algo::BlockOps,
|
||||
arithmetic::{FieldOps, WrappingOps},
|
||||
fbobj::{FBObj, FBObjTrait},
|
||||
fbobj::FBObjTrait,
|
||||
packing::Packing,
|
||||
};
|
||||
|
|
Loading…
Reference in New Issue