1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61
/// The name that is used in the GPU source code to identify the item that is used.
pub trait GpuName {
/// A unique name for the item.
///
/// To make the uniqueness easier to implement, use the [`name`] macro. It produces a unique
/// name, based on the module path and the type of the item itself. That identifier might not
/// be stable across different versions of a crate, but this is OK as kernel sources/binaries
/// are always bundled with a library and not re-used between versions.
///
/// # Example
///
/// ```
/// struct Fp;
///
/// impl ec_gpu::GpuName for Fp {
/// fn name() -> String {
/// ec_gpu::name!()
/// }
/// }
/// ```
fn name() -> String;
}
/// A prime field that returns the values in a representation that is suited for the use on a GPU.
pub trait GpuField: GpuName {
/// Returns `1` as a vector of 32-bit limbs in little-endian non-Montgomery form (least
/// significant limb first).
fn one() -> Vec<u32>;
/// Returns `R ^ 2 mod P` as a vector of 32-bit limbs in little-endian non-Montgomery form
/// (least significant limb first).
fn r2() -> Vec<u32>;
/// Returns the field modulus as a vector of 32-bit limbs in non-Montgomery form (least
/// significant limb first).
fn modulus() -> Vec<u32>;
/// If the field is an extension field, then the name of the sub-field is returned.
fn sub_field_name() -> Option<String> {
None
}
}
/// Macro to get a unique name of an item.
///
/// The name is a string that consists of the module path and the type name. All non-alphanumeric
/// characters are replaced with underscores, so that it's an identifier that doesn't cause any
/// issues with C compilers.
#[macro_export]
macro_rules! name {
() => {{
let mod_path = module_path!();
let type_name = core::any::type_name::<Self>();
let name = if type_name.starts_with(mod_path) {
type_name.into()
} else {
[mod_path, "__", type_name].concat()
};
name.replace(|c: char| !c.is_ascii_alphanumeric(), "_")
}};
}