boo-rs 0.1.3

Encrypt primitives types at compile time
Documentation
use proc_macro2::TokenStream;
use quote::quote;
use syn::parse::{Parse, ParseStream};
use syn::{Block, Expr, Token};

/// Parsed `boo_branch!(cond { .. } else { .. })` invocation.
///
/// Branch bodies are re-emitted unmodified; only the dispatch between them is obscured.
pub struct Branch {
    /// Boolean-valued condition, evaluated exactly once.
    cond: Expr,
    /// Block run when `cond` is `true`.
    then_branch: Block,
    /// Block run when `cond` is `false`.
    else_branch: Block,
}

impl Parse for Branch {
    fn parse(input: ParseStream) -> syn::Result<Self> {
        let cond = Expr::parse_without_eager_brace(input)?;
        let then_branch = input.parse()?;
        input.parse::<Token![else]>()?;
        let else_branch = input.parse()?;

        Ok(Self {
            cond,
            then_branch,
            else_branch,
        })
    }
}

impl Branch {
    /// Rewrites into an opaque-predicate dispatch: which branch runs is decided by an XOR-masked
    /// comparison instead of a direct test of `cond`.
    ///
    /// Routes `mask`, `target`, and the XOR result through [`core::hint::black_box`]: without it,
    /// a release build folds the dispatch straight back to a direct test of `cond` (`mask` and
    /// `target` are related by `target = mask ^ 1`).
    ///
    /// # Arguments
    ///
    /// * `site_salt` - see [`crate::call_site_salt`].
    pub fn obscure(self, site_salt: u64) -> TokenStream {
        let Self {
            cond,
            then_branch,
            else_branch,
        } = self;
        let mask = site_salt as u8;
        let target = mask ^ 1;

        quote! {
            {
                let __boo_mask: u8 = ::core::hint::black_box(#mask);
                let __boo_target: u8 = ::core::hint::black_box(#target);
                let __boo_selector: u8 = ::core::hint::black_box(((#cond) as u8) ^ __boo_mask);
                if __boo_selector == __boo_target #then_branch else #else_branch
            }
        }
    }
}